在JavaScript中,我们可以动态创建<style>
元素并附加到<head>
部分,以便为大量元素应用CSS规则。
这种方法的优缺点是什么?
如果与javascript迭代元素相比,它确实提供了性能提升。幕后的内容(浏览器内部)?
哪一个更快或更慢? Javascript迭代元素或在浏览器中动态添加css?
处理时间怎么样?处理负荷?
为了更好地理解我使用此方法的问题,请参阅以下示例:
示例:如果我的表格包含20个或更多列以及1000行或更多行,请执行以下html:
<table border="1" class='no-filter'>
<thead>
<tr>
<th data-title='id'>Id</th>
<th data-title='name'>Name</th>
<th data-title='family_name'>Family Name</th>
<th data-title='ssn'>SSN</th>
//Other table data
</tr>
</thead>
<tbody>
<tr data-id='1' data-name='nick' data-famil_name='jackson' data-ssn='123456'>
<td class="column column1">1</td>
<td class="column column2">Nick</td>
<td class="column column3">Jackson</td>
<td class="column column4">123456</td>
//Other table data
</tr>
//Other rows
<tr data-id='809' data-name='helga' data-famil_name='jhonson' data-ssn='125648'>
<td class="column column1">809</td>
<td class="column column2">Helga</td>
<td class="column column3">Jhonson</td>
<td class="column column4">125648</td>
//Other table data
</tr>
//Other rows
<tr data-id='1001' data-name='nick' data-famil_name='jhonson' data-ssn='216458'>
<td class="column column1">1001</td>
<td class="column column2">Nick</td>
<td class="column column3">Jhonson</td>
<td class="column column4">216458</td>
//Other table data
</tr>
//Other rows
</tbody>
</table>
如果有人需要jsFiddle示例,我可以稍后创建一个。
案例1:如果我想动态隐藏只包含SSN数据的表列。我可以应用几种方法来做到这一点。这种方法可分为两大类。在第一类解决方案中,我可以迭代td
元素并动态更改列的样式。在第二种方法中,我可以通过here动态创建一个或使用@Frits van Campen给定的预定义CSS规则来应用CSS。 (注意: @Frits van Campen对于给定的案例是很好的解决方案。但我想进一步讨论,然后操纵表格行显示和隐藏。)
我可以创建动态CSS规则,如下所示:
td:nth-child(3)
{
display:none;
}
或应用预定义的CSS规则:
table.no-filter td.column3
{
display:block;
}
table.filter3 td.column3
{
display: none;
}
以下是jsFiddly示例:
这是使用console.time方法进行时间比较,我发现here。
左边是动态css,右边是迭代方法。
也许,它不合适,因为它计算追加样式元素与迭代元素。动态CSS中元素的所有迭代都将由浏览器内部完成。但是如果我们认为我们的脚本响应时间动态css更快。 注意:与jQuery相比,纯JavaScript中的迭代方法会更快。但是我没有结果多快。所以你的答案可以更多。
案例2 现在,我想要突出显示包含名称为“Nick”的用户的表格行<tr>
。在这里你可以注意到表行有数据属性,如name,family_name,id等。所以,这里我可以再次使用javascript或任何其他库工具迭代元素或者可以应用一些动态规则(我不知道是否可能或者不应用预定义的过滤器,如1)。
CSS规则:
tr[data-name ~='nick']
{
background-color:red;
}
在这种情况下,我可以通过动态应用CSS规则来进行很多有趣的过滤。
更新:此处给出的示例仅用于简单概述问题。并且一些优化的迭代可以在javascript中同样快速地执行。但是我只考虑没有北斗儿子元素的表比较嵌套的ul元素,其中遍历以便选择元素可能是困难的。
重要提示:我这里只给出表格示例,以便澄清我遇到的问题,如果无关紧要,请随时编辑问题并删除此部分。另外,请在问题范围内明确说明您的答案。在这里,我不是在问'我是否以良好的方式实施了?'我想知道动态创建样式元素在浏览器内部机制方面有什么优点或缺点。
P.S。例如:为什么我有这个想法?我最近回答了'How to hide columns in very long html table'问题。在这个问题中,OP询问是否对长表中的某些表列应用CSS规则。我建议在飞行中创建带有规则的样式元素,它工作正常。我认为这是因为浏览器内部机制应用了样式,并且比迭代元素和将样式应用于每个项目提供了更好的性能。
答案 0 :(得分:4)
除了一些范围问题(页面上可能有更多表格......)这种方法没有任何本质上的错误 - DOM中的style
元素可以根据您的需要进行编辑,浏览器遵循标准遵守标准。在你的测试用例中,实际上并没有真正有效的其他方法,因为确实colgroup
有非常混乱的支持 - 在Bugzilla中有78个重复的错误,而且Mozilla一直拒绝正确实现它the first related bug report in 1998
它更快的原因只是开销之一 - 一旦组装完整的DOM,可以在本机C ++中应用相对较小的样式表,这比Javascript解释器可以遍历所有行和单元格要快得多。这是因为历史上CSS规则是反向应用的,浏览器会快速保存字典,以便查找所有td
个元素。 Native C ++将始终击败更复杂的基于解释器的代码。
将来,范围问题也可以通过scoped styles来解决(目前仅在FF中,相当典型),您的编码方式如下:
<table>
<style id="myTableStyle" scoped>
td:nth-child(1) { display:none }
</style>
<tbody>
...
</tbody>
</table>
scoped
属性使包含的样式仅对其包含元素有效,在这种情况下为table
,当然还包含所有包含的元素。由于您可以通过ID访问它,因此内容很容易被替换/重建。
虽然这比您的方法更好,但只要没有通用浏览器支持style
中创建head
元素就是最好的解决方法。
答案 1 :(得分:4)
动态生成CSS不好。不要这样做。
通过生成动态CSS工作的解决方案可以转换为不需要动态CSS的解决方案。
如果您需要示例,请在此处查看我的回答:jQuery to update actual CSS
直接回复您关联的案例:
这对我来说似乎是一个非常奇怪的用例。具有1000行表的页面已经是一个糟糕的起始位置。您无法在屏幕上合理地容纳1000行,并期望进行任何有用的交互。 CSS不是问题所在。如果表格较小,性能问题就会消失。
可能还有其他方法,而不是OP建议的方法。您不需要(动态地)为每个单元格添加一个类,您可以将该类放在生成时间,例如:
<table class="no-filter">
...
<td class="filter1 filter2"></td>
...
</table>
然后有类似的东西:
table.filter1 td.filter2 { display: none; }
table.filter2 td.filter1 { display: none; }
您只需更改表格上的类,以说明适用的过滤器。
CSS不仅仅是一把锤子,它是一套非常精致且功能强大的工具。确保使用正确的。
拥有静态CSS的优点应该是显而易见的:
还有一些性能问题。我可以看到浏览器供应商优化了AGAINST动态CSS。我的意思是,如果静态CSS的优化降低了动态CSS的性能,那么你可能会做出这种权衡。
答案 2 :(得分:-1)
有一个名为less.js的库,它允许你在你的.css文件中使用变量操作css。这是一个非常好的库,你可能想看看它。 http://www.lesscss.org/