CSS特异性中的点是如何计算的
研究特异性我偶然发现了这个博客 - http://www.htmldog.com/guides/cssadvanced/特异性/
它指出特异性是 CSS 的一种评分系统。它告诉我们元素值 1 分,类值 10 分,ID 值 100 分。它还在上面说这些点被总计,并且总数是该选择器的特异性。
例如:
身体 = 1 分
body .wrapper = 11 分
body .wrapper #container = 111 点
因此,使用这些点,我预计以下 CSS 和 HTML 会导致文本呈蓝色:
#a {
color: red;
}
.a .b .c .d .e .f .g .h .i .j .k .l .m .n .o {
color: blue;
}
<div class="a">
<div class="b">
<div class="c">
<div class="d">
<div class="e">
<div class="f">
<div class="g">
<div class="h">
<div class="i">
<div class="j">
<div class="k">
<div class="l">
<div class="m">
<div class="n">
<div class="o" id="a">
This should be blue.
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
当 15 个类等于 150 分而 1 个 ID 等于 100 分时,为什么文本是红色的?
显然,这些分数不仅仅是总计;而是。它们是串联的。在这里阅读更多相关信息 - http://www.stuffandnonsense.co.uk/archives/css_specificity_wars .html
这是否意味着我们选择器中的类 = 0,0,15,0
OR 0,1,5,0
?
(我的直觉告诉我是前者,因为我们知道 ID 选择器的特殊性如下所示:0,1,0,0
)
Researching specificity I stumbled upon this blog - http://www.htmldog.com/guides/cssadvanced/specificity/
It states that specificity is a point-scoring system for CSS. It tells us that elements are worth 1 point, classes are worth 10 points and IDs are worth 100 points. It also goes on top say that these points are totaled and the overall amount is that selector's specificity.
For example:
body = 1 point
body .wrapper = 11 points
body .wrapper #container = 111 points
So, using these points, I expect the following CSS and HTML to result in the text being blue:
#a {
color: red;
}
.a .b .c .d .e .f .g .h .i .j .k .l .m .n .o {
color: blue;
}
<div class="a">
<div class="b">
<div class="c">
<div class="d">
<div class="e">
<div class="f">
<div class="g">
<div class="h">
<div class="i">
<div class="j">
<div class="k">
<div class="l">
<div class="m">
<div class="n">
<div class="o" id="a">
This should be blue.
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
Why is the text red when 15 classes would equal 150 points compared to 1 ID which equals 100 points?
Apparently the points aren’t just totaled; they’re concatenated. Read more about that here - http://www.stuffandnonsense.co.uk/archives/css_specificity_wars.html
Does that mean that the classes in our selector = 0,0,15,0
OR 0,1,5,0
?
(my instincts tell me it’s the former, as we KNOW the ID selector’s specificity looks like this: 0,1,0,0
)
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(7)
Pekka 的答案实际上是正确的,并且可能是思考这个问题的最佳方式。
然而,正如许多人已经指出的那样,W3C CSS 建议指出“连接三个数字 abc(在具有大基数的数字系统中)可以提供特殊性”。所以我内心的极客只需要弄清楚这个基地有多大。
事实证明,实现此标准算法所采用的“非常大的基数”(至少 4 个最常用的浏览器*)是 256 或 28。
这意味着使用 0 个 id 和 256 个类名指定的样式将覆盖仅使用 1 个 id 指定的样式。我用一些小提琴测试了这一点:
255 个类不足以足以覆盖 1 个 id< /a>
...但是 256 个类足以覆盖 1 个 id
...和 256 个标记名足以覆盖 1 个类名
...但是,唉,256 个 id 不足以覆盖 1 个内联style (2012/8/15 更新 - 你必须使用
!important
)因此,实际上存在一个“点系统”,但它不是以 10 为基数。而是以 256 为基数。以下是方法它的工作原理是:
(28)2 或 65536,乘以选择器中的 id 数量
这不是'对于传达概念的粗略练习来说非常实用。
这可能就是有关该主题的文章一直使用基数 10 的原因。
***** [Opera 使用 216(请参阅 karlcow 的评论)。其他一些选择器引擎使用无穷 - 实际上没有积分系统(请参阅 Simon Sapin 的评论)。]
更新,2014 年 7 月:
正如 Blazemonger 在今年早些时候指出的那样,webkit 浏览器(Chrome、Safari)现在似乎使用比 256 更高的基数。也许是 216,就像 Opera 一样? IE 和 Firefox 仍使用 256。
2021 年 3 月更新:
Firefox 不再使用 256 作为基础。
Pekka's answer is practically correct, and probably the best way to think about the issue.
However, as many have already pointed out, the W3C CSS recommendation states that "Concatenating the three numbers a-b-c (in a number system with a large base) gives the specificity." So the geek in me just had to figure out just how large this base is.
It turns out that the "very large base" employed (at least by the 4 most commonly-used browsers*) to implement this standard algorithm is 256 or 28.
What this means is that a style specified with 0 ids and 256 class-names will over-ride a style specified with just 1 id. I tested this out with some fiddles:
255 classes are not enough to override 1 id
...but 256 classes are enough to override 1 id
...and 256 tag-names are enough to override 1 class-name
...but, alas 256 ids are not enough to override 1 inline style (Updated 2012/8/15 -- you'll have to use
!important
)So there is, effectively, a "point system," but it's not base 10. It's base 256. Here's how it works:
(28)2 or 65536, times the number of ids in the selector
This isn't very practical for back-of-the-envelop exercises to communicate the concept.
That's probably why articles on the topic have been using base 10.
***** [Opera uses 216 (see karlcow’s comment). Some other selector engines use infinity — effectively no points system (see Simon Sapin’s comment).]
Update, July 2014:
As Blazemonger pointed out earlier in the year, webkit browsers (Chrome, Safari) now appear to use a higher base than 256. Perhaps 216, like Opera? IE and Firefox still use 256.
Update, March 2021:
Firefox no longer uses 256 as a base.
好问题。
我不能确定 - 我设法找到的所有文章都避免了多个类的示例,例如 这里 - 但我假设在比较类选择器和 ID 之间的特异性时,类的计算方式为无论该值多么详细,都只能是
15
值。这符合我对特异性行为的经验。
然而,必须有一些类的堆叠,因为
比我唯一的解释更具体
的是,堆叠类的特殊性仅针对彼此计算,而不针对 ID 计算。
更新:我现在已经明白了一半。它不是计分制,有关 15 分的班级信息是不正确的。这是一个由 4 部分组成的编号系统,此处对此进行了很好的解释。
起点是4位数字:
根据W3C关于特异性的解释,上述规则的具体值是:
这是一个具有非常大(未定义?)基数的编号系统。
我的理解是,因为基数很大,所以第4列中的任何数字都无法击败> > 的数字。第 3 列中为 0,第 2 列、第 1 列也相同......这是正确的吗?
我很感兴趣是否有比我更懂数学的人可以解释计数系统以及当单个元素大于 9 时如何将其转换为十进制。
Good question.
I can't tell for sure - all the articles I manage to find avoid the example of multiple classes, e.g. here - but I assume that when it comes to comparing the specifity between a class selector and an ID, the class gets calculated with a value of
15
only, no matter how detailed it is.That matches my experience in how specificity behaves.
However, there must be some stacking of classes because
is more specific than
the only explanation I have is that the specificity of stacked classes is calculated only against each other but not against IDs.
Update: I half-way get it now. It is not a points system, and the information about classes weighing 15 points is incorrect. It is a 4-part numbering system very well explained here.
The starting point is 4 figures:
According to the W3C explanation on specificity, the specificty values for the abovementioned rules are:
this is a numbering system with a very large (undefined?) base.
My understanding is that because the base is very large, no number in column 4 can beat a number > 0 in column 3, the same for column 2, column 1 .... Is this correct?
I'd be interested whether somebody with a better grasp at Math than me could explain th numbering system and how to convert it to decimal when the individual elements are larger than 9.
当前的选择器级别 4 工作草案很好地描述了 CSS 中的特异性:
这意味着值 A、B 和 C 彼此完全独立。
15 个类别不会为您的选择器提供 150 分的特异性分数,而是为其提供 15 的 B 值。单个 A 值足以压倒这一点。
作为一个比喻,想象一个由 1 名祖父母、1 名父母和 1 名孩子组成的家庭。这可以表示为1,1,1。如果父母有 15 个孩子,这不会突然使他们成为另一个父母 (1,2,0)。这意味着父母比只有 1 个孩子 (1,1,15) 承担的责任要多得多。 ;)
同一文档还接着说:
添加此内容是为了解决 Faust 的答案 中提出的问题,即 2012 年的 CSS 实现允许特异性值溢出到每个其他。
早在 2012 年,大多数浏览器就实现了 255 的限制,但这个限制是允许溢出的。 255 个类的 A,B,c 特异性得分为 0,255,0,但 256 个类溢出并具有 A,B,c 得分1,0,0。突然我们的 B 值变成了 A 值。选择器级别 4 文档通过声明永远不允许限制溢出来彻底解决这个问题。通过此实现, 255 和 256 类将具有相同的 A,B,c 分数 0,255,0。
Faust 的回答中给出的问题已在大多数现代浏览器中修复。
The current Selectors Level 4 Working Draft does a good job of describing Specificity in CSS:
This means that the values A, B and C are completely independent of each other.
15 classes doesn't give your selector a specificity score of 150, it gives it a B value of 15. A single A value is enough to overpower this.
As a metaphor, imagine a family of 1 grand parent, 1 parent and 1 child. This could be represented as 1,1,1. If the parent has 15 children, that doesn't suddenly make them another parent (1,2,0). It means that the parent has an awful lot more responsibility than they had with just 1 child (1,1,15). ;)
The same documentation also goes on to say:
This has been added to tackle the problem presented in Faust's answer, whereby CSS implementations back in 2012 allowed specificity values to overflow into each other.
Back in 2012, most browsers implemented a limitation of 255, but this limitation was allowed to overflow. 255 classes had an A,B,c specificity score of 0,255,0, but 256 classes overflowed and had an A,B,c score of 1,0,0. Suddenly our B value became our A value. The Selectors Level 4 documentation completely irradiates that problem by stating that the limit can never be allowed to overflow. With this implementation, both 255 and 256 classes would have the same A,B,c score of 0,255,0.
The problem given in Faust's answer has since been fixed in most modern browsers.
我目前正在使用CSS Mastery:高级 Web 标准解决方案这本书。
第一章第 16 页说:
(强调我的)和
继续假设您通常可以以 10 为基数进行计算,但前提是所有列的值都小于 10。
在您的示例中,id 不值 100 分;每个都值得
[0, 1, 0, 0]
分。因此,一个 id 胜过 15 个类,因为在高基数系统中[0, 1, 0, 0]
大于[0, 0, 15, 0]
。I am currently using the book CSS Mastery: Advanced Web Standards Solutions.
Chapter 1, page 16 says:
(emphasis mine) and
It goes on to say that you can often do the calculation in base-10, but only if all columns have values less than 10.
In your examples, ids are not worth 100 points; each is worth
[0, 1, 0, 0]
points. Therefore, one id beats 15 classes because[0, 1, 0, 0]
is greater than[0, 0, 15, 0]
in a high-base number system.我喜欢将特异性排名与奥运会奖牌榜进行比较(金牌优先法——首先根据金牌数量,然后是银牌,然后是铜牌)。
它也适用于您的问题(一个特异性组中有大量选择器)。特异性分别考虑每组。在现实世界中,我很少看到有超过十几个选择器的情况)。
此处还提供了非常好的特异性计算器。您可以将示例(#a 和 .a .b .c .d .e .f .g .h .i .j .k .l .m .n .o)放在那里并查看结果。
2016 年里约奥运会奖牌榜示例如下
I am fond of comparison of Specificity ranking to Olympic Games medal table (gold first method — based first on the number of gold medals, then silver and then bronze).
It works also with your question (huge number of selectors in one specificity group). Specificity considered each group separately. In real world I've very rarely seen case with more than a dozen selectors).
There is also quite good specificity calculator available here. You can put your example (#a and .a .b .c .d .e .f .g .h .i .j .k .l .m .n .o) there and see the results.
Example of Rio 2016 Olympic Games medal table looks like
我不相信博客的解释是正确的。规范在这里:
http://www.w3.org/TR/CSS2 /cascade.html#specificity
类选择器中的“点”加起来不会比“id”选择器更重要。它只是不那样工作。
I don't believe that the blog's explanation is correct. The specification is here:
http://www.w3.org/TR/CSS2/cascade.html#specificity
"Points" from a class selector can't add up to be more important than an "id" selector. It just doesn't work like that.
我想说的是:
我认为它们只会叠加到取决于你得到的东西,如果它是相同的倍数。
因此,类将始终覆盖元素,ID 始终覆盖类,但如果它下降到 4 个元素中的哪一个,其中 3 为蓝色,1 为红色,则它将是蓝色。
例如:
应该变成红色。
参见示例http://jsfiddle.net/RWFWq/
“如果有5件事说红色和 3 说蓝色很好,我会变成红色”
I would say that:
I think they only stack into depending what you get if it is multiple of the same.
So a Class will always overide the element and ID always over the Class but if it is down to which of 4 elements where 3 is to blue and 1 is to red it will be blue.
For Example:
Should turn out red.
See Example http://jsfiddle.net/RWFWq/
"if 5things say red and 3 say blue well Ima go red"