首先简单举个例子:
HTML:
<div class="text" id="text">
文本
</div>
CSS:
#text {
color: red
}
.text {
color: blue
}
以上最终文本应该是什么颜色呢?答案是红色。大家可能都知道ID选择器的优先级会比类名的选择器优先级高,所以最终颜色为红色。
优先级的计算规则
大家写过css的应该都知道,css的优先级关系如下:
内联样式 > ID选择器 > 类名选择器 > 标签 (暂且先不考虑!important的情况)
但是浏览器具体的优先级算法是什么样的呢?《CSS REFACTORING》中提到了算法的过程。
A specificity is determined by plugging numbers into (a, b, c, d):
-
If the styles are applied via the style attribute, a=1; otherwise, a=0
-
b is equal to the number of ID selectors present.
-
c is equal to the number of class selectors, attribute selectors, and pseudoclasses present.
-
d is equal to the number of type selectors and pseudoelements present.
意思就是:
优先级是由 a 、b、c、d 的值来决定的,其中它们的值计算规则如下:
-
如果存在内联样式,那么
a=1,否则a=0 -
b的值等于ID选择器出现的次数 -
c的值等于类选择器出现的次数 +伪类出现的次数 +属性选择器出现的次数
-
d的值等于标签选择器出现的次数 +伪元素出现的次数
再举个🌰:
#text > ul > li > a.link {}
使用上面的算法可得:
- 因为没有内联样式,所以a=0
ID选择器出现的次数为1,所以b=1类选择器出现的次数为1,所以c=1标签选择器出现的次数为3,所以d=3
以上可以简写为:(0,1,1,3)
到这里大家可能已经知道优先级是如何进行计算的了,但是知道怎么算该如何比较两个优先级的高低呢?
比较的规则是:从左向右依次进行比较,较大的胜出,如果相等则继续往右移一位进行比较。如果四位全部相同,则后面的会覆盖前面的。
继续举🌰:
HTML:
<div id="parent" class="parent">
<div class="child">
123
</div>
<div class="child">
456
</div>
</div>
CSS:
#parent {
.child {
color: red
}
}
.parent {
.child {
color: blue
}
}
算出#parent .child的优先级为(0, 1, 1, 0),.parent .child的优先级为(0, 0, 2, 0)。可以算出左边第一位都是0,那么就去比较第二位,前者的第二位为1,后者的为0。所以前者的优先级比后者的大,因此为红色。
优先级的特殊情况
经过上面的优先级计算规则可知,内联样式的优先级最高。但是!important的优先级比内联样式的优先级还要高,如果不是为了要覆盖内联样式,应该尽量避免使用!important。
当然,可能有的人会想,是不是在内联样式中使用了!important,外部无论怎么修改都没有办法了呢。确实是这样,因此建议大家千万不要再内联样式中使用!important。