深入CSS优先级

4,209 阅读4分钟
现在越来越多的CSS框架,比如Bootstrap,flat UI等等。当我们使用这些UI框架时,由于审美不一样或某些爱好,我们或多或少会去修改一些样式,当然,直接修改源文件是一个方法,但这是一个笨方法,并不推荐。这时,我们就需要自己写一些样式去覆盖,有时你会发现无效或只是一部分起作用,这就是涉及到CSS优先级的问题了。

1. 什么是优先级
优先级就是分配给指定的CSS声明的一个权重,它由匹配的选择器中的每一种选择器类型的数值 决定。

CSS优先级:内联(style="") > 内联样式表(<style>) | 外链样式表(<link>) > 浏览器缺省

注:内联样式表外链样式表取决于定义的位置顺序。
选择器优先级:ID选择器 > 类选择器 | 属性选择器 | 伪类选择器 > 元素选择器

例外的 !important: 当在一个样式声明中使用一个!important 规则时,此声明将覆盖任何其他声明
2. 网上教程权重计算
关于CSS权重,网上教程大都按不同选择器给了权重值:

STYLE:1000#ID:100.CLASS 10ELEMENT 1

一张CSS权重关系图:

实例:
<p class="myClass" id="myDiv">   


div#myDiv { color: purple; }    1-0-0  
p.myClass { color: red;}			0-1-1  
p[id^='my'] {color: blue;}			0-1-1  
p:nth-of-type(1n) {color: yellow;}	0-1-1
注:基于CSS权重值,普遍是正确的,但N级复杂样式定义还未有空去测试。

3. 案例
3.1 精确度
div#test span { color: green }  
span { color: red }  
div span { color: blue }   


<div id="test">   
  <span>Text</span>  
</div>
在线实例
在这里多提一句,浏览器CSS匹配不是从左到右进行查找,而是从右到左进行查找。比如div#main p span.red{color:red;},浏览器的查找顺序如下:先查找html中所有class='red'的span元素,找到后,再查找其父辈元素中是否有p元素,再判断p的父元素中是否有id为main的div元素,如果都存在则匹配上。

好处:浏览器从右到左进行查找的好处是为了尽早过滤掉一些无关的样式规则和元素

3.2 !important
div#test span { color: green }  
span { color: red !important; /*注意这里*/ }  
div span { color: blue }   


<div id="test">   
  <span>Text</span>  
</div>
在线实例
!important会提升优先级,可以说是优先级最高。

注:如果要覆盖一个!important,可以用另一个!important覆盖它。

3.3 同类型
.class3 {color: blue}   
.class1 {color: green;}     
.class2 {color: red;}   


<span class="class1 class2 class3"> 我是红色,class2生效</span>
在线实例
从上面的例子中可以看到,三个class类型,最后生效的是样式表中定义最后的,而不是class中定义最后的。

3.4 无视DOM树中的距离

body h1 {   
  color: green;  
}  
div h1 {   
  color: red;  
}  
html h1 {   
  color: purple;  
}   


<div>   
  <h1>Here is a title!</h1>  
</div>
在上面的样式中,都是以标签选择器 标签选择器这种后代选择器的形式来定义样式,可以看到最终显示的样式中定义最后的。

3.5 :not()
div.outer p {   
  color:orange;  
}  
div:not(.outer) p {   
  color: lime;  
}   


<div class="outer">   
  <p>This is in the outer div.</p>   
  <div class="inner">   
    <p>This text is in the inner div.</p>   
  </div>  
</div>
:not 否定伪类在优先级计算中不会被看作是伪类,而是当作普通选择器来处理。

总结

  • 样式表的元素选择器选择越精确,则其中的样式优先级越高
  • 对于相同类型选择器制定的样式,在样式表文件中,越靠后的优先级越高
  • 特殊的!important会覆盖前面所有的声明


参考:

developer.mozilla.org/zh-CN/docs/…

www.standardista.com/css3/css-sp…