您的位置:首页 > Web前端 > CSS

css的效率是怎么样的呢,浏览器渲染的速度又如何呢(css,html渲染效率)

2010-10-06 17:22 681 查看
我承认我并不经常想这个问题......我们写的css的效率是怎么样的呢,浏览器渲染的速度又如何呢?

这是应该是浏览器开发者应该关心的(页面加载更快,用户就会更愉快)。Mozilla有一篇文章: about best practices
. Google 当然也很关心这个问题,他们也有这样一篇文章:Optimize browser rendering


让我们了解下他们主要倡导的东东,然后讨论他们的实用性。

从右到左

浏览器如何读取你的CSS选择器有一个很重要的原则,那就是它们从右到左读取。这意味这像 ul > li
a[title="home"] 这样的选择器,a[title="home"] 将是最先被读取的。这一部分通常被称为 “key
selector” (可否称为“目标选择器” -_-!)选择器的最后一部分,也是被选择的标签。

ID's 是最有效率的,通用符是最慢的

有四种目标选择器:ID, class, tag和通用符
。看下他们各自的效率如何:

#main-navigation { } /* ID (最快) */

body.home #page-wrap { } /* ID */

.main-navigation { } /* Class */

ul li a.current { } /* Class *

ul { } /* Tag */

ul li a { } /* Tag */

* { } /* Universal (最慢) */

#content [title='home'] /* Universal */ 然后我们结合从右到左和目标选择器的概念,我们可以知道下面这个选择器并不高效:

#main-nav > li { } /* 看着很快实则很慢 */

尽管这让人有点费解......因为ID's是最高效的,浏览器可以通过ID迅速的找到 li。但事实是,li 标签是被先读取的。

不要用标签修饰


死也不要像下面这样干:

ul#main-navigation { }

ID's 是唯一的,所以不需要用标签修饰,这只会让它更低效。

如果你可以避免的话,也不要用它修饰 class 。class 不是唯一的,所以理论上你可以把它用在不同的标签。如果你愿意的话,你可以用标签控制不同的样式,这样你可能需要标签修饰(比如:li.first),但这样做的人很少,所以,don't .

绝对没有比用后代选择器更糟糕的做法了

David Hyatt:

后代选择器是CSS里最昂贵的选择器,昂贵得可怕——特别是当它放在标签和通用符后面时。

就如下面这个东东一样,绝对的效率毒瘤:

html body ul li a { }

一个选择器渲染失败比这个选择器被渲染更高效


我不是很确定是否有更好的证据去证明这一点,因为如果你有大量的选择器在CSS样式表里无法找到,这样的事情貌似很离奇,但一点必需注意的是,从右到左的解释一个选择器来说,一旦它找不到,那它就会停止尝试。然而如果它找到了,那它就需要花更多精力去解释了。

试想一下为何你这样写选择器

思考下这东东:

#main-navigation li a { font-family: Georgia, Serif; }

你可能不需要从 a 选择器开始(如果你只是想换个字体)。下面这个可能更高效些:

#main-navigation { font-family: Georgia, Serif; }

实用性

还刻前面提到的Mozilla的一篇文章?已经有十年了。事实是:计算机比十年前变慢了(不是我理解错了,还是作者想说现在的WEB越来越复杂了)。我感
觉这东东在当年似乎还更受重视。十年前我还是个21岁的英俊小生,当然我不觉得那里我会认识css这东东。所以我也无法跟你讲以前的情况......但我
觉得渲染效率的问题之所以没被重视是因为这从来就不是一个大问题。

这是我的一些看法:不管怎样上面提到的东东都是有意义的,你可以按照上面的方法去做,因为它并不会限制你的CSS制作。但你也没必要太教条主义。如果你是
个完美主义者,而之前又没有考虑过那东东,那是时候去重新看一下你之前写的一些样式是否有改进的地方了。如果你没发现你的网站明显的渲染缓慢,那大可别太
在意,在以后的工作中多注意就行了。

超级快速,零实用性

我们知道ID's 是最高效的选择器。当你想让渲染速度最高效时,你可能会给每个独立的标签配置一个ID,然后用这些ID写样式。那会超级快,也超级荒唐。这样的结果是语义极差,维护难到了极点。即使在核心部分你也不应该见过这样做的。我认为这个可以提醒我们不要为了高效的CSS放弃语义和可维护性。

Thanks to Jason Beaudoin for emailing me about the idea. If anyone
knows more about this stuff, or if you have additional tips that you
use in this same vein, let’s hear it!

顺便提一下,因为CSS选择器被很多javascript库使用,上面提到的东东仍然适用,ID选择器还是最快的,后代选择器和类似的东东比较慢。

css中ID的渲染效率真的比class高吗?我的css渲染测试

本来这个东西是想拿到交流会上去讨论的,今天看到http://bbs.blueidea.com/thread-2985630-1-1.html][译
] 如何使CSS渲染更高效[/url]

感觉说法过于片面

我就把我的东西提前拿出来吧

[color=DarkRed]首先讲几个前提:[/color]

--------------------------------------------

css渲染分三种情况

1.首次加载渲染

2.css和html调用缓存渲染

3.html文件调用缓存渲染

渲染的顺序

ff,chrome,safari,opera 最新版本的浏览器是在加载的同时进行css样式的渲染和展现(或者说是同步进行)。

而ie 8 是在文档加载完成后展现,而在渲染过程中是无法见到网页展现的

渲染效率与什么有关?

1.css选择器的查询定位效率

2.浏览器的渲染模式和算法

3.要进行渲染内容的大小

--------------------------------------------

[color=DarkRed]测试:[/color]

OS :win xp

硬件:内存 4G,CPU 酷睿4核

web容器:tomcat 6.0

浏览器 :ff 3.6/ie 8

test1.html

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd
">

<html xmlns="http://www.w3.org/1999/xhtml
">

<head>

<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />

<title>Untitled Document</title>

<style type="text/css">

.box p{ background-color:blue;}

</style>

</head>

<body>

<div class="box" id="wrap">

<p>hihihihihihihihihihihihihihihihihi</p>

.....此处省去8万行代码

</div>

</body>

</html>

test2.html

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd
">

<html xmlns="http://www.w3.org/1999/xhtml
">

<head>

<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />

<title>Untitled Document</title>

<style type="text/css">

#wrap p{ background-color:red;}

</style>

</head>

<body>

<div class="box" id="wrap">

<p>hihihihihihihihihihihihihihihihihi</p>

.....此处省去8万行代码

</div>

</body>

</html>

ff结果对比:

选择器 首次载入 刷新页面 修改background-color值后刷新

.box p 4.82s 3.86s 4.10s

#wrap p 5.89s 3.62s 4.86s

ie8结果对比:

选择器 首次载入 刷新页面 修改background-color值后刷新

.box p 6.32s 6.06s 6.33s

#wrap p 6.30s 6.31s 6.17s

结论:

[color=Red]很明显可以看出ff下class选择器效率略高于id选择器,而ie8下则不相上下。[/color]

问题:

渲染是什么时候开始的,或者说是什么时候开始运算的?

渲染是在文档完成之前,之后还是同时?(平时我们看到页面内容展现时,似乎这3中情况都存在)

对CSS渲染效率的一些研究

其实在平时很少注意到CSS渲染效率的问题,不过在很多时候都是细节决定成败,这也是个不容忽视的问题。之前也拜读过网上流传的一篇有关CSS渲染效率的文章,传得太多,也不知原作是谁了。不过并不是太赞同其中的一些观点,所以就本人工作中的一些经验以及看法,说说这个问题,个人观点并非权威,欢迎拍砖。

在这里我们不只是单纯地研究渲染效率的快或慢,应该从一个项目的整体来看。页面渲染的这个过程,是在用户本地进行的,也就是说用户打开页面,载入了HTML代码以及样式表、JS等等相关的文件,浏览器再跟据这些文件把页面渲染出来。关于速度方面,我们更注重的是载入的速度。而渲染速度,的确某些样式的写法会存在渲染速度的差异,但对于当前随便每秒都能运算上亿次的个人电脑来说,把一张背景图平铺100次跟平铺10000次又有多大区别呢?当然,细节,细节决定成败,但细节不等于吹毛求疵,下面说说个人对此侧重点的一些看法。

可能会有影响,但可跟据具体情况忽略的部分

比如说颜色值,color:#F00;、color:#FF0000;、color:red; 这三者都是一样的,至少用人类的感观无法区分其对渲染速度的影响,用简写可能或多或少能减少那么几个字节的体积,不过标准写法是6位大写字符的写法。

display与visibility就不详说了,这本身就是两种不同的表现属性,该用谁就用谁。

注意某些样式的保留属性,比如说:

background:url(image.jpg);这样一句,那么在渲染的时候会默认输出background-color : transparent 、background-attachment : scroll 、background-repeat : repeat 等等属性。在完美主义者的眼里这是对资源的一种浪费,但同样,人类的感观体会不到此影响。其实个人还是认为简写形式有助于减少样式表的体积,而且这也似乎是行内默认的写法了。同样的,border、list-style等也有默认属性,也不用深究了。

背景平铺的问题

对于可平铺的背景来说,很多人喜欢用1px为单位来进行平铺,前面也说了,其实平铺多少次对于个人电脑来说几乎都是一样的,关键在于图片的大小了。对于可平铺的图片,一定范围内的像素值是一样的,所以增大尺寸对于积体的影响并不大,我这里对比了单色1*1跟10*10的图片在jpg跟gif格式下的大小,相差都几有几个字节



其实本人不太建议用1px的图,至少自己在修改的时候无法一眼看出那张图片是什么。而且现在用css sprites也会把可平铺的部分也做进去,这也是对渲染效率的提升了。

再说说会有明显影响的部分

@import 的使用

不建议在页面里使用,他会在页面加载完之后才被加载,有可能使页面闪动或是裸体。如果是样式表过多为了方面管理的话,放在CSS里就好。

某些选择符的使用

渲染的过程也就是对这些选择符的匹配,所以我们可以很容易地理解到,一些比较直接的选择符比如类选择符、ID选择符等的匹配效率高,而一些条件比较繁复点的选择符比如子选择符、属性选择符等的匹配效率相对来就低一些。当所匹配的量比较多的时候,可以明显地感觉到速度的差别。(关于各种选择符,具体可查看CSS手册了);浏览器如何读取你的CSS选择器有一个很重要的原则,那就是它们从右到左读取

IE的滤镜

自从标准化的兴起以来,IE滤镜的日子就不好过了,除了不兼容以外,某些滤镜真的蛮耗资源的。现在还在用的可能就是为了处理IE6下图片透明的问题了,建议能不用就不用他吧。

expression的使用

也许这个不能归为渲染的部分,不过他的确相当占资源,如果加得多的话,会让你的页面其慢如牛。

自从标准化的兴起以来,IE滤镜的日子就不好过了,除了不兼容以外,某些滤镜真的蛮耗资源的。现在还在用的可能就是为了处理IE6下图片透明的问题了,建议能不用就不用他吧。

expression的使用

也许这个不能归为渲染的部分,不过他的确相当占资源,如果加得多的话,会让你的页面其慢如牛。

一下是其他的一些建议:

1.

十六进制的颜色值对位数与大小写

编写十六进制颜色值时你可能会用小写字母或省略成3位数,关于这写法没找到确实的数据证明对浏览器的渲染效率是否有影响,但十六进制的颜色值默认标准是大写及6位数标注。在未知情况下不希望冒险而降低了渲染的效率。

* 不赞成 - color:#f3a;

* 建议用 - color:#FF33AA;

2.

display与visibility的差异

他们用于设置或检索是否显示对象。display隐藏对象不保留物理空间,visibility为隐藏对象保留占据的物理空间。当浏览器渲染被占据的物理空间时,会有所消耗资源。

* 不赞成 - visibility:hidden;

* 建议用 - display:none;

3.

border:none;与border:0;的区别

和display与visibility的关系类似,分别不保留与保留空间。更多的是border:0;尽管可以隐藏掉边框,但它会为你保留border-color/border-style的使用权。

* 不赞成 - border:0;

* 建议用 - border:none;

4.

不宜过小的背景图片平铺

一张宽高1px的背景图片,虽然文件体积非常之小,但渲染宽高500px的板块需要重复平铺250000(贰拾伍万)次。提高背景图片渲染效率跟图片尺寸及体积有关,最大的图片文件体积保持约70KB。

* 不赞成 - 宽高8px以下的平铺背景图片

* 建议用 - 衡量适中体积及尺寸的背景图片

5.

IE的滤镜

IE的滤镜除了比较消耗资源外也有兼容性问题。当中有令PNG透明的滤镜,可采用GIF或JPG似透非透的办法来避免使用此滤镜。建议只在IE6应用GIF透明,因为IE7以上已经支持了PNG透明。

* 不赞成,滥用IE滤镜因为消耗资源外也有兼容性问题。

* 建议用,最好选择其它方法能避免使用滤镜。

6.

*{ margin:0; padding:0;}避免浏览器样式差异
(在上边的css选择器的优先级中进行了详细的讲解)

*号通配符把所有标签都初始化一遍,浏览器的渲染消耗一定的资源。有部分在标签在不同浏览器上几乎无差异,或是某些已经不推荐使用的标签(因为你不会去用它),它们不需通配符要重新初始化一遍这样做能节省一点资源。

* 不赞成,使用*号通配符

* 不赞成,div span button b table等标签纳入通配符控制内外填充样式

* 建议用,有选择性地使用通配符控制内外填充样式。

7.

不要添加额外的标签来描述class或id
(在上边的css选择器的优先级中进行了详细的讲解)

如果你有一个选择器是以id作为关键选择符,请不要添加多余标签名上去。因为ID是唯一的,你不要为了一个不存在的理由而降低了匹配的效率。

* 不赞成 - button#backButton { }

* 不赞成 - .menu-left #newMenuIcon { }

* 建议用 - #backButton { }

* 建议用 - #newMenuIcon { }

8.

尽量选择最特殊的类来存放选择器
(在上边的css选择器的优先级中进行了详细的讲解)

降低系统效率的一个最大原因是我们在标签类中用了过多的选择符。通过添加 class 到元素,我们可以将类别进行再细分为 class 类,这样就不用为了一个标签浪费时间去匹配过多的选择符了。

* 不赞成 - treeitem[mailfolder="true"] > treerow > treecell { }

* 建议用 - .treecell-mailfolder { }

9.

避免子孙选择符
(在上边的css选择器的优先级中进行了详细的讲解)

子孙选择符是CSS中最耗资源的选择符。他真的是非常的耗资源,尤其是在选择器使用标签类或通用类的时候。很多情况中,我们真正想要的是子选择符。除非有明确说明,在 UI CSS 中是严禁使用子孙选择符的。

* 不赞成 - treehead treerow treecell { }

* 好一点,但还是不行(参照下一条) - treehead > treerow > treecell { }

10.

标签类中不要包含子选择符
(在上边的css选择器的优先级中进行了详细的讲解)

不要在标签类中使用子选择符。否则,每次元素的出现,都会额外地增加匹配时间。(特别是当选择器似乎多半会被匹配的情况下)

* 不赞成 - treehead > treerow > treecell { }

* 建议用 - .treecell-header { }

11.

留意所有子选择符的使用
(在上边的css选择器的优先级中进行了详细的讲解)

小心地使用子选择符。如果你能想出一个的不使用他的方法,那么就不要使用。特别是在 RDF 树和菜单会频繁地使用子选择符,像这样。

* 不赞成 - treeitem[IsImapServer="true"] > treerow > .tree-folderpane-icon { }

请记住 RDF 的属性是可以在模板中被复制的!利用这一点,我们可以复制那些想基于该属性改变的子 XUL 元素上的 RDF 属性。

* 建议用 - .tree-folderpane-icon[IsImapServer="true"] { }
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: 
相关文章推荐