2012-02-22 61 views
4

我正在使用大型表格在Web應用程序的頁面上工作。在某些情況下,可以使用12列和多達300行。我很難讓表格在Internet Explorer中快速呈現。我複製我的困難在此位的測試代碼:Internet Explorer緩慢渲染通過JavaScript生成的表格

http://jsfiddle.net/dSFz5/

上英特爾四核Q8200 4GB內存與IE9的一些基準測試:
50行,12列:432ms
100行, 12列:1023ms
200行,12列:2701ms
400行,12列:8107ms
800行,12列:24619ms

指數級差。

我設法挖掘了一些代碼,這些代碼在Internet Explorer中顯示的速度相當快,但由於我使用了mustache.js模板來呈現單元格和行(保留所有HTML標記超出我的JavaScript),我不能夠使用這些DOM方法:

http://jsfiddle.net/bgzLG/

基準測試結果:
50行,12列:僅爲37微秒
100行,12列:72ms的
200行,12列:146ms
4 00行,12列:324ms
800行,12列:566ms

我無法構造塊表塊像在第二示例中,由於與客戶端模板我需要注入HTML的串由鬍子回來。如果你開始粘貼.innerHTML的內容,那麼表演坦克會再次出現。

任何人都可以推薦一種方法來建立一個更高效的方式與客戶端模板的使用兼容嗎?

分頁是處理此問題的一種方法,但我想自己解決問題。

任何建議非常感謝!

+0

我認爲這是DOM遍歷,你在循環的每一次迭代中做的事情,然後是DOM操作12次,這是在殺死它。儘可能少地觸摸DOM。做任何可以處理的東西,然後將其添加到DOM。 – 2012-02-22 06:45:22

回答

5

首先,我建議從實際創建表分離出弦的創作,因爲它的問候渲染時間造成的開銷。接下來,您應該嘗試在將其附加到主體之前創建整個表格,以最大限度地減少重新繪製/重新焊接的數量。最後,我建議在IE中加入一個數組,因爲該瀏覽器中的字符串連接會爲每個副本重複分配更大和更大的內存塊。當你使用數組連接時,瀏覽器只分配足夠的內存來保存整個字符串。

var strings = [], 
    table = ['<table>'], 
    i, j; 

for (i = 0; i < 1000; i += 1) { 
    strings[i] = []; 

    for (j = 0; j < 12; j += 1) { 
     strings[i][j] = randomString(); 
    }   
} 

var start = new Date().getTime(); 

for (i = 0; i < 1000; i += 1) { 
    table.push('<tr>'); 

    for (j = 0; j < 12; j += 1) { 
     table.push('<td>', strings[i][j], '</td>'); 
    } 

    table.push('</tr>'); 
} 

table.push('</table>'); 

$('body').append(table.join('')); 

var end = new Date().getTime(); 
var time = end - start; 
alert('Execution time: ' + time + 'ms');​ 

使用這種方法,我得到如下結果在IE9:

100 rows is ~9ms 
200 rows is ~19ms 
500 rows is ~51ms 
1000 rows is ~119ms 
5000 rows is ~526ms 

我敢肯定,我們可以進一步優化,但是這應該是足夠足夠容納300行(〜30毫秒),這就是你說你的目標是。對於任何用戶界面交互,它也保持在低於50ms的聖盃基準下。

+0

你需要50個聲望來評論你不屬於你的帖子。如果你不斷回答問題,你應該可以在幾個小時內得到它:) – 2012-02-22 07:20:56

+0

看起來好像我的評論消失了。 :( 感謝您的支持,雖然我已經更新了我的答案,包括基準測試和一些解釋,希望OP能看到它 – 2012-02-22 08:06:28

+0

這真是太棒了爲了使您的解決方案適用於我的代碼,我必須編寫一個函數類添加到DOM後收集和綁定元素的事件(通過元素ID),但最終不會使代碼複雜化,並且運行速度非常快,對於IE6和IE7用戶,這是您唯一的方式可以在瀏覽器端創建具有事件處理的大型表格,IE6和IE7無法在內存中處理構建大型DOM元素。 – 2012-02-29 18:00:31

0

我會說模板在這裏不適合,因爲性能的原因。而且,首先使用所有行對DOM進行操作來構建表,然後纔可以追加它。它有很大的不同。

你也可以嘗試類似jqGrid的東西:它處理大量的行,而只有可見的行在html(虛擬列表)中呈現在屏幕上。

2

使用此:

var table = $('<table></table>'); 

for (var a=0; a<200; a++) { 


    var tr = $('<tr></tr>');  
    for (var b=0; b<12; b++) { 

     tr.append('<td>'+randomString()+'</td>');   

    } 

table.append(tr); 
} 

$('body').append(table); 

颳了約130MS。在將其添加到DOM之前,這是在內存中構建表。

這裏是我的基準:

 
100 - 346 
200 - 670 
500 - 2037 
1000 - 4272 
2000 - 10502 

And your original: 

100 - 408 
200 - 898 
500 - 2987 
1000 - 10202 
2000 - 41305 

+0

Jquery是非常酷的東西:)越少觸摸DOM,越好。祝你好運! – 2012-02-22 07:07:46

相關問題