【前端性能優(yōu)化】之代碼級優(yōu)化

1. Javascript

DOM

DOM操作應(yīng)該是腳本中最耗性能的一類操作晌砾,例如增加、修改哼勇、刪除 DOM元素或者對 DOM集合進行操作积担。如果腳本中包含了大量的 DOM操作則需要注意以下幾點:

  1. HTML Collection(HTML收集器,返回的是一個數(shù)組內(nèi)容信息)

在腳本中 document.images先誉、document.forms 褐耳、getElementsByTagName()返回的都是 HTMLCollection類型的集合渴庆,在平時使用的時候大多將它作為數(shù)組來使用把曼,因為它有 length屬性漓穿,也可以使用索引訪問每一個元素晃危。不過在訪問性能上則比數(shù)組要差很多,原因是這個集合并不是一個靜態(tài)的結(jié)果震叮,它表示的僅僅是一個特定的查詢苇瓣,每次訪問該集合時都會重新執(zhí)行這個查詢從而更新查詢結(jié)果偿乖。所謂的 “訪問集合” 包括讀取集合的 length屬性贪薪、訪問集合中的元素。

因此竣稽,當你需要遍歷 HTML Collection的時候毫别,盡量將它轉(zhuǎn)為數(shù)組后再訪問,以提高性能忘闻。即使不轉(zhuǎn)換為數(shù)組齐佳,也請盡可能少的訪問它债沮,例如在遍歷的時候可以將 length屬性疫衩、成員保存到局部變量后再使用局部變量。

  1. Reflow & Repaint

除了上面一點之外童芹, DOM操作還需要考慮瀏覽器的 Reflow和Repaint 假褪,因為這些都是需要消耗資源的近顷,具體的可以參加以下文章:

慎用 with

with(obj){ p = 1}; 代碼塊的行為實際上是修改了代碼塊中的執(zhí)行環(huán)境窒升,將obj放在了其作用域鏈的最前端饱须,在 with代碼塊中訪問非局部變量是都是先從 obj上開始查找,如果沒有再依次按作用域鏈向上查找譬挚,因此使用 with相當于增加了作用域鏈長度殴瘦。而每次查找作用域鏈都是要消耗時間的号杠,過長的作用域鏈會導(dǎo)致查找性能下降。

因此立帖,除非你能肯定在 with代碼中只訪問 obj中的屬性晓勇,否則慎用 with灌旧,替代的可以使用局部變量緩存需要訪問的屬性枢泰。

避免使用 eval和 Function

每次 eval 或 Function 構(gòu)造函數(shù)作用于字符串表示的源代碼時,腳本引擎都需要將源代碼轉(zhuǎn)換成可執(zhí)行代碼窿克。這是很消耗資源的操作 —— 通常比簡單的函數(shù)調(diào)用慢 100倍以上年叮。

eval 函數(shù)效率特別低玻募,由于事先無法知曉傳給 eval 的字符串中的內(nèi)容补箍,eval在其上下文中解釋要處理的代碼坑雅,也就是說編譯器無法優(yōu)化上下文衬横,因此只能有瀏覽器在運行時解釋代碼蜂林。這對性能影響很大。

Function 構(gòu)造函數(shù)比 eval略好矮锈,因為使用此代碼不會影響周圍代碼 ;但其速度仍很慢苞笨。

此外瀑凝,使用 eval和 Function也不利于Javascript 壓縮工具執(zhí)行壓縮。

減少作用域鏈查找(這方面設(shè)計到一些內(nèi)容的相關(guān)問題)

前文談到了作用域鏈查找問題谚中,這一點在循環(huán)中是尤其需要注意的問題宪塔。如果在循環(huán)中需要訪問非本作用域下的變量時請在遍歷之前用局部變量緩存該變量囊拜,并在遍歷結(jié)束后再重寫那個變量蝌麸,這一點對全局變量尤其重要,因為全局變量處于作用域鏈的最頂端艾疟,訪問時的查找次數(shù)是最多的来吩。

低效率的寫法:

    // 全局變量
    var globalVar = 1;
    function myCallback(info){
      for( var i = 100000; i--;){
      //每次訪問 globalVar 都需要查找到作用域鏈最頂端,本例中需要訪問 100000 次
      globalVar += i;
      }        
    }

更高效的寫法:

// 全局變量
  var globalVar = 1;
  function myCallback(info){
  //局部變量緩存全局變量
  var localVar = globalVar;
  for( var i = 100000; i--;){
      //訪問局部變量是最快的
      localVar += i;
  }
  //本例中只需要訪問 2次全局變量 蔽莱,在函數(shù)中只需要將 globalVar中內(nèi)容的值賦給localVar 中區(qū)
     globalVar = localVar;
 }

此外弟疆,要減少作用域鏈查找還應(yīng)該減少閉包的使用。

數(shù)據(jù)訪問

Javascript中的數(shù)據(jù)訪問包括直接量 (字符串盗冷、正則表達式 )怠苔、變量仪糖、對象屬性以及數(shù)組柑司,其中對直接量和局部變量的訪問是最快的,對對象屬性以及數(shù)組的訪問需要更大的開銷锅劝。當出現(xiàn)以下情況時攒驰,建議將數(shù)據(jù)放入局部變量:

  1. 對任何對象屬性的訪問超過 1次
  2. 對任何數(shù)組成員的訪問次數(shù)超過 1次
    另外,還應(yīng)當盡可能的減少對對象以及數(shù)組深度查找故爵。

字符串拼接

在 Javascript中使用"+" 號來拼接字符串效率是比較低的玻粪,因為每次運行都會開辟新的內(nèi)存并生成新的字符串變量,然后將拼接結(jié)果賦值給新變量诬垂。與之相比更為高效的做法是使用數(shù)組的 join方法劲室,即將需要拼接的字符串放在數(shù)組中最后調(diào)用其 join方法得到結(jié)果。不過由于使用數(shù)組也有一定的開銷结窘,因此當需要拼接的字符串較多的時候可以考慮用此方法很洋。

關(guān)于 Javascript優(yōu)化的更詳細介紹請參考:

2. CSS選擇符

在大多數(shù)人的觀念中,都覺得瀏覽器對 CSS選擇符的解析式從左往右進行的隧枫,例如

#toc A { color: #444; }

這樣一個選擇符喉磁,如果是從右往左解析則效率會很高棺克,因為第一個 ID選擇基本上就把查找的范圍限定了,但實際上瀏覽器對選擇符的解析是從右往左進行的线定。如上面的選擇符娜谊,瀏覽器必須遍歷查找每一個 A標簽的祖先節(jié)點,效率并不像之前想象的那樣高斤讥。

3. HTML

對 HTML本身的優(yōu)化現(xiàn)如今也越來越多的受人關(guān)注了

4. Image壓縮

圖片壓縮是個技術(shù)活纱皆,不過現(xiàn)如今這方面的工具也非常多,壓縮之后往往能帶來不錯的效果芭商,具體的壓縮原理以及方法在《 Even Faster Web Sites》第10 章有很詳細的介紹派草,有興趣的可以去看看。

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末铛楣,一起剝皮案震驚了整個濱河市近迁,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌簸州,老刑警劉巖鉴竭,帶你破解...
    沈念sama閱讀 212,599評論 6 492
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異岸浑,居然都是意外死亡搏存,警方通過查閱死者的電腦和手機,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 90,629評論 3 385
  • 文/潘曉璐 我一進店門矢洲,熙熙樓的掌柜王于貴愁眉苦臉地迎上來璧眠,“玉大人,你說我怎么就攤上這事读虏≡鹁玻” “怎么了?”我有些...
    開封第一講書人閱讀 158,084評論 0 348
  • 文/不壞的土叔 我叫張陵盖桥,是天一觀的道長灾螃。 經(jīng)常有香客問我,道長葱轩,這世上最難降的妖魔是什么睦焕? 我笑而不...
    開封第一講書人閱讀 56,708評論 1 284
  • 正文 為了忘掉前任,我火速辦了婚禮靴拱,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘猾普。我一直安慰自己袜炕,他們只是感情好,可當我...
    茶點故事閱讀 65,813評論 6 386
  • 文/花漫 我一把揭開白布初家。 她就那樣靜靜地躺著偎窘,像睡著了一般乌助。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上陌知,一...
    開封第一講書人閱讀 50,021評論 1 291
  • 那天他托,我揣著相機與錄音,去河邊找鬼仆葡。 笑死赏参,一個胖子當著我的面吹牛,可吹牛的內(nèi)容都是我干的沿盅。 我是一名探鬼主播把篓,決...
    沈念sama閱讀 39,120評論 3 410
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼腰涧!你這毒婦竟也來了韧掩?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 37,866評論 0 268
  • 序言:老撾萬榮一對情侶失蹤窖铡,失蹤者是張志新(化名)和其女友劉穎疗锐,沒想到半個月后,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體费彼,經(jīng)...
    沈念sama閱讀 44,308評論 1 303
  • 正文 獨居荒郊野嶺守林人離奇死亡窒悔,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 36,633評論 2 327
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發(fā)現(xiàn)自己被綠了敌买。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片简珠。...
    茶點故事閱讀 38,768評論 1 341
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖虹钮,靈堂內(nèi)的尸體忽然破棺而出聋庵,到底是詐尸還是另有隱情,我是刑警寧澤芙粱,帶...
    沈念sama閱讀 34,461評論 4 333
  • 正文 年R本政府宣布祭玉,位于F島的核電站,受9級特大地震影響春畔,放射性物質(zhì)發(fā)生泄漏脱货。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點故事閱讀 40,094評論 3 317
  • 文/蒙蒙 一律姨、第九天 我趴在偏房一處隱蔽的房頂上張望振峻。 院中可真熱鬧,春花似錦择份、人聲如沸扣孟。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,850評論 0 21
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽凤价。三九已至鸽斟,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間利诺,已是汗流浹背富蓄。 一陣腳步聲響...
    開封第一講書人閱讀 32,082評論 1 267
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留慢逾,地道東北人立倍。 一個月前我還...
    沈念sama閱讀 46,571評論 2 362
  • 正文 我出身青樓,卻偏偏與公主長得像氛改,于是被迫代替她去往敵國和親帐萎。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 43,666評論 2 350

推薦閱讀更多精彩內(nèi)容