真实的国产乱ⅩXXX66竹夫人,五月香六月婷婷激情综合,亚洲日本VA一区二区三区,亚洲精品一区二区三区麻豆

成都創(chuàng)新互聯(lián)網(wǎng)站制作重慶分公司

各種動態(tài)渲染Element方式的性能分析

本篇內(nèi)容介紹了“各種動態(tài)渲染Element方式的性能分析”的有關(guān)知識,在實際案例的操作過程中,不少人都會遇到這樣的困境,接下來就讓小編帶領(lǐng)大家學(xué)習(xí)一下如何處理這些情況吧!希望大家仔細閱讀,能夠?qū)W有所成!

創(chuàng)新互聯(lián)是一家專注于成都做網(wǎng)站、網(wǎng)站設(shè)計與策劃設(shè)計,廣靈網(wǎng)站建設(shè)哪家好?創(chuàng)新互聯(lián)做網(wǎng)站,專注于網(wǎng)站建設(shè)十載,網(wǎng)設(shè)計領(lǐng)域的專業(yè)建站公司;建站業(yè)務(wù)涵蓋:廣靈等地區(qū)。廣靈做網(wǎng)站價格咨詢:028-86922220

一、性能優(yōu)化的原則及方法論

樹立原則:動態(tài)渲染進入一個Dom元素,首先需要保證動態(tài)渲染操作必須盡可能少對原有dom樹的影響,影響重繪及重排。

確定方法論:必須尋找一個容器來緩存渲染期間生成的dom結(jié)構(gòu)(操作必須盡可能少對原有dom樹的影響),然后再進行一次渲染到目標element中。

二、生成期間DOM緩存的選擇

  • DocumentFragment(文檔碎片對象,選擇原因:脫離于文檔流)

  • 臨時Element(選擇原因:新element脫離于文檔流)

    • 臨時Element+innerHTML+cloneNode返回最外層element元素對象,再進行插入appendChild,必要時還需要選擇器方法講某一個Element對象提取出來

    • XML字符串通過解析生成Element對象(注意,不是HTMLxxxElement對象,是Element對象),然后將該對象appendChild進去

    • createElement,再一步步進行渲染

    • 通過描述Dom的String(下稱:DomString),轉(zhuǎn)化為Dom對象

  • 臨時字符串(選擇原因:借助innerHTML渲染,一次渲染)

三、DocumentFragment的優(yōu)缺點

基本模式:

var fragment = document.createDocumentFragment();     fragment.appendChild(         ...    //生成Element的IIFE     )
//IIFE示例,根據(jù)配置創(chuàng)建元素 var ConfigVar = {   ELname:"div",   id:"blablabla",   name:"balblabla",   class:"ClassName" } (function(Config){       var el = document.createElement(Config.ELname);           el.className = (Config.class || "");     for (let AttrName in Config){           if (AttrName == "class")continue;           el.setAttribute(AttrName,Config[AttrName]);     }       return el; })(ConfigVar)

優(yōu)點

1、脫離于文檔流,操作不會對Dom樹產(chǎn)生影響

2、在每一次生成臨時Element時候就可以將該Element對象的引用保存下來,而不需要多次用選擇器再次獲取。

缺點

兼容性只是達到IE9+

四、createElement的優(yōu)缺點

基本模式

var el = document.createElement("ElementName");         el.className = "";     el.setAttribute("AttrName",AttrValue);     el.setAttribute("AttrName",AttrValue);     ...     el.appendChild(                   ... //生成Element的IIFE,見上文     );

優(yōu)點

1、新創(chuàng)建的元素脫離于文檔流,操作不會對Dom樹產(chǎn)生影響

2、兼容性***

3、在每一次生成臨時Element時候就可以將該Element對象的引用保存下來,而不需要多次用選擇器再次獲取。

缺點

每一次調(diào)用setAttribute方法都是一次次對Element進行修改,此處具有潛在的性能損耗。

五、DomString——臨時Element+innerHTML+cloneNode的優(yōu)缺點

基本模式

var domString2Dom = (function(){     if (window.HTMLTemplateElement){         var container = document.createElement("template");         return function(domString){             container.innerHTML = domString;             return container.content.firstChild.cloneNode(true)         }     }else{         //對不支持的template 的瀏覽器還有兼容性方法沒寫,所以不支持tr,td等些元素inner進div中。         var container = document.createElement("div");         return function(domString){             container.innerHTML = domString;             return container.firstChild.cloneNode(true)         }             } })();
var template = domString2Dom('
'); for (var index = 0; index < 80; index++) {       template.appendChild(     (function(){       var el = domString2Dom("
M
");       return el     })()   )                 }

優(yōu)點

創(chuàng)建Dom之后不需要多次進行setAttribute

缺點

1、臨時元素不能包裹一些特定的元素(不能在所有瀏覽器的所有 HTML 元素上設(shè)置 innerHTML 屬性)

2、解析的過程進行了很多其余的操作。此處具有潛在的性能損耗。

3、插入的字符串***層Node只允許有一個元素

六、DomString——XML解析的優(yōu)缺點

基本模式

var XMLParser = function () {     var $DOMParser = new DOMParser();     return function (domString) {         if (domString[0] == "<") {             var doc = $DOMParser.parseFromString(domString, "application/xhtml+xml");             return doc.firstChild;         }         else {             return document.createTextNode(domString);         }     }; }();
var template = XMLParser('
'); for (var index = 0; index < 80; index++) {   template.appendChild((function () {     var el = XMLParser("
M
");     return el;   })()); }

優(yōu)點

DomString方法中通用性***的,雖然IE10+才支持DOMParser,但是IE9以下的有替代方法

缺點

1、解析的過程本身就具有潛在的性能損耗。

2、只能得到剛剛創(chuàng)建最外層元素的克隆。子元素的引用還需要用選擇器。

3、插入的字符串***層Node只允許有一個元素

七、臨時字符串的優(yōu)缺點

基本模式:

var template = document.createElement("div"); template.innerHTML = `                         Test TextNode                         ${(function(){                           var temp = new Array(8);                           for (var index = 0; index < 80; index++) {                             temp[index]="
M
"                           }                           return temp.join()                         }())}                       
` //需要增加的一大段Element

優(yōu)點

1、通用性***,不需要逐步創(chuàng)建一大堆無用的Element對象引用

2、運用es6模板字符串編碼優(yōu)雅,不需要字符串用加號進行鏈接

缺點

1、如果是直接給出配置Config進行渲染需要進行字符串的生成

2、只能得到剛剛創(chuàng)建最外層元素的引用。子元素的引用還需要用選擇器。

八、Template元素

由于HTML5中新增了template元素

其特點就是有一個content屬性是HTMLDocumentFragment對象,所以可以包容任何元素

基本范式是:

var template = document.createElement("template"); template.innerHTML = `                         Test TextNode                         ${(function(){                           var temp = new Array(8);                           for (var index = 0; index < 80; index++) {                             temp[index]="
M
"                           }                           return temp.join()                         }())}                       ` //需要增加的一大段Element // template.content 是HTMLDocumentFragment

優(yōu)點

比div要好很多,作為臨時元素容器的包容性更強

缺點

在不支持的瀏覽器中表示為HTMLUnknownElement

九、各種方法的效率對比

測試代碼:(由于筆者不太熟悉各種瀏覽器性能的BUG,這里的代碼如果有不足請指正),代碼由typescript進行編寫,也可以用babel進行編譯。

/**  * @param Count:渲染DOM結(jié)構(gòu)的次數(shù)  */ var DateCount = {     TimeList : {},     time:function(Str){         console.time(Str);     },     timeEnd:function(Str){         console.timeEnd(Str);     } }; //==================工具函數(shù)====================== var domString2Dom = (function () {     var container;     if (window.HTMLTemplateElement) {         container = document.createElement("template");         return function (domString) {             container.innerHTML = domString;             return container.content.firstChild.cloneNode(true);         };     }     else {         //對不支持的template 的瀏覽器還有兼容性方法沒寫,所以不支持tr,td等些元素inner進div中。         container = document.createElement("div");         return function (domString) {             container.innerHTML = domString;             return container.firstChild.cloneNode(true);         };     } })(); var XMLParser = (function () {     var $DOMParser;     if (window.DOMParser) {         $DOMParser = new DOMParser();         return function (domString) {             if (domString[0] == "<") {                 var doc = $DOMParser.parseFromString(domString, "application/xhtml+xml");                 return doc.firstChild;             }             else {                 return document.createTextNode(domString);             }         };     }else{         $DOMParser = new ActiveXObject("Microsoft.XMLDOM");         return function (domString) {             if (domString[0] == "<") {                 $DOMParser.async = false;                 $DOMParser.loadXML(domString);                    return $DOMParser             }             else {                 return document.createTextNode(domString);             }                         }      }  })(); //===============================================  var Test = function(Count){     //保留這種寫法,能夠在移動端平臺中不依靠控制臺進行效率測試     // var DateCount = {     //     TimeList : {},     //     time:function(Str){     //         this.TimeList[Str] = Date.now();     //     },     //     timeEnd:function(Str){     //         alert(Str+(Date.now() - this.TimeList[Str]));     //     }     // }          //基準測試1:     DateCount.time("無臨時div + 不需要字符串拼接 + innerHTML:")     for (let index = 0; index < Count; index++) {         (function(){             var template = document.createElement("div");                 template.className = "TestClass";                 template.setAttribute("Arg","TestArg")                 template.innerHTML = ` Test TextNode MMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMM ` //需要增加的一大段Element,共100個子級div             return template         }())       }     DateCount.timeEnd("無臨時div + 不需要字符串拼接 + innerHTML:")      //基準測試2:     DateCount.time("createElement+appendChild寫法:")     for (let index = 0; index < Count; index++) {         (function(){             var template = document.createElement("div");                 template.className = "TestClass";                 template.setAttribute("Arg","TestArg")                  template.appendChild(document.createTextNode('Test TextNode'));                 for (let index = 0; index < 100; index++) {                     let element = document.createElement("div");                         element.setAttribute("child","true");                         element.appendChild(document.createTextNode("M"))                         template.appendChild(element)                 }             return template         }())       }     DateCount.timeEnd("createElement+appendChild寫法:")          //DocumentFragment      DateCount.time("DocumentFragment+ createElement+appendChild 寫法:")     for (let index = 0; index < Count; index++) {         (function(){             var fragment = document.createDocumentFragment();                 fragment.appendChild(function(){                     var template = document.createElement("div");                         template.className = "TestClass";                         template.setAttribute("Arg","TestArg")                          template.appendChild(document.createTextNode('Test TextNode'));                         for (let index = 0; index < 100; index++) {                             let element = document.createElement("div");                                 element.setAttribute("child","true");                                 template.appendChild(element)                         }                     return template;                 }());              return fragment         }())       }     DateCount.timeEnd("DocumentFragment+ createElement+appendChild 寫法:")          //DomString——臨時Element+innerHTML+cloneNode     // DateCount.time("DomString——臨時Element+innerHTML+cloneNode:")     // for (let index = 0; index < Count; index++) {     //     (function(){     //         var template = domString2Dom('');     //         for (let index = 0; index < 100; index++) {         //             template.appendChild(     //                 (function(){     //                     var el = domString2Dom("M");     //                     return el     //                 })()     //             )                     //         }     //         return template;     //     }())       // }     // DateCount.timeEnd("DomString——臨時Element+innerHTML+cloneNode:")          //DomString——XML解析     // DateCount.time("DomString——XML解析:")     // for (let index = 0; index < Count; index++) {     //     (function(){     //         var template = XMLParser('');     //         for (let index = 0; index < 100; index++) {     //             template.appendChild((function () {     //                 var el = XMLParser("M");     //                 return el;     //             })());     //         }     //     }())       // }     // DateCount.timeEnd("DomString——XML解析:")         //臨時div + 臨時字符串拼接:     DateCount.time("臨時div + 字符串拼接:")     for (let index = 0; index < Count; index++) {         (function(){             let template = document.createElement("div");             template.innerHTML = `                                     Test TextNode                                     ${(function(){                                         let temp = "";                                         for (let index = 0; index < 100; index++) {                                             temp+="M"                                         }                                         return temp                                     }())}                                 ` //需要增加的一大段Element             return template.firstChild;          }())       }     DateCount.timeEnd("臨時div + 字符串拼接:")      //臨時template + 臨時字符串拼接:     DateCount.time("臨時template + 字符串拼接:")     for (let index = 0; index < Count; index++) {         (function(){             var template = document.createElement("template");             template.innerHTML = `                                     Test TextNode                                     ${(function(){                                         let temp = "";                                         for (let index = 0; index < 100; index++) {                                             temp+="M"                                         }                                         return temp                                     }())}                                 ` //需要增加的一大段Element             return template.content;          }())       }     DateCount.timeEnd("臨時template + 字符串拼接:")      //臨時template + createElement+appendChild 寫法     DateCount.time("template + createElement+appendChild 寫法:")     for (let index = 0; index < Count; index++) {         (function(){             var template = document.createElement("template");                 template.appendChild(function(){                     var template = document.createElement("div");                         template.className = "TestClass";                         template.setAttribute("Arg","TestArg")                          template.appendChild(document.createTextNode('Test TextNode'));                         for (let index = 0; index < 100; index++) {                             let element = document.createElement("div");                                 element.setAttribute("child","true");                                 template.appendChild(element)                         }                     return template;                 }());             return template.content          }())       }     DateCount.timeEnd("template + createElement+appendChild 寫法:")  };  for (var key of [1,10,100,1000]) {     console.log("Start"+key);     Test(key); }

“各種動態(tài)渲染Element方式的性能分析”的內(nèi)容就介紹到這里了,感謝大家的閱讀。如果想了解更多行業(yè)相關(guān)的知識可以關(guān)注創(chuàng)新互聯(lián)網(wǎng)站,小編將為大家輸出更多高質(zhì)量的實用文章!


網(wǎng)頁題目:各種動態(tài)渲染Element方式的性能分析
標題URL:http://weahome.cn/article/pephdh.html

其他資訊

在線咨詢

微信咨詢

電話咨詢

028-86922220(工作日)

18980820575(7×24)

提交需求

返回頂部