2009-05-22 2 views
0

while文は、IE/Firefoxで(4-5秒間、ページの読み込みを防止する)遅すぎる実行されますが、高速のサファリで効率化ページが開き、テキストが理想的な幅に達するまで切り捨てます。は、それは上のテキストのピクセル幅を測定しています...</p> <p>をjQueryの機能で、この機能で

function constrain(text, ideal_width){ 

    $('.temp_item').html(text); 
    var item_width = $('span.temp_item').width(); 
    var ideal = parseInt(ideal_width); 
    var smaller_text = text; 
    var original = text.length; 

    while (item_width > ideal) { 
     smaller_text = smaller_text.substr(0, (smaller_text.length-1)); 
     $('.temp_item').html(smaller_text); 
     item_width = $('span.temp_item').width(); 
    } 

    var final_length = smaller_text.length; 
    if (final_length != original) { 
     return (smaller_text + '&hellip;'); 
    } else { 
     return text; 
    } 
} 

パフォーマンスを改善する方法はありますか?これをバブルソート関数に変換するにはどうすればよいですか?

ありがとうございます!

+0

これは実際にソートの問題ではなく、バブルソートはあなたができる最速のソートです。 – Soviut

答えて

5

$()の呼び出しをループ外に移動し、その結果を一時変数に格納します。その関数を実行することは、.html()の呼び出しを除いて、コード内で最も遅いものになるでしょう。

ライブラリーのセレクターエンジンを高速で作成するのは非常に難しい作業ですが、通常のjavascript操作(ローカルスコープで変数を検索するなど)と比べて遅いです。そのようなクラスセレクタを使用している場合は、jqueryは基本的に各クラス属性を調べて正規表現を実行するドキュメント内のすべての要素をループする必要があります。毎回ループを回る!可能な限りタイトなループからそのようなものを奪いましょう。 Webkitは.getElementsByClassNameを持っているので、他のブラウザはそうしないので、速く実行します。 (まだ)。

+0

これは確かに妥当と思われ、自分で試したことはありません。 DOMに短い文字列を挿入するhtml()の呼び出しも関係しているかどうか(つまり、それらがレンダリングをトリガーするかどうか) –

+0

はい、うまくいくはずです。 DRYの原則に沿って、コードを高速化しますが、おそらくもっと重要なのは、保守が簡単です。 たとえば、temp_itemが実際にクラスではなくidであることがわかっている場合は、コードを4か所で変更する必要があります。ミス1とあなたはしばらくあなたの髪を引っ張っているかもしれません。 ブルトンの提案に従えば、1回だけ変更するだけです。 –

4

理想的な幅になるまで1文字を削除する代わりに、binary searchを使用できます。

2

私は、temp_itemのhtmlを設定して幅を読み取ることで、ループ内のDOMを常に変更していることがわかりました。

問題のコンテキストはわかりませんが、レンダリングされた要素を測定してレイアウトを調整しようとするのは、私の立場からは妥当ではありません。

多分あなたは別の角度から問題に近づくかもしれません。固定幅に切り捨てるのが一般的です。

その他の可能性(ハック?)選択肢がない場合は、コンテナ要素のオーバーフローCSSプロパティを使用して&hellipを置くことができます。テキストの隣の他の要素私はあなたが意図している方法で問題を解決する必要性を再考することをお勧めしますが、

ヒューゴは、ブルトンの提案以外

2

、あなたのアルゴリズムを高速化するための別の可能性は、テキストの長さのバイナリ検索を使用することです。現在は、一度に1文字ずつ長さを減らしています - これは文字列の長さのO(N)です。代わりに、O(log(N))になる検索を使用します。注意すべき

function constrain(text, ideal_width){ 

...

var temp_item = $('.temp_item'); 
    var span_temp_item = $('span.temp_item'); 

    var text_len_lower = 0; 
    var text_len_higher = smaller_text.length; 

    while (true) { 
      if (item_width > ideal) 
      { 
      // make smaller to the mean of "lower" and this 
      text_len_higher = smaller_text.length; 
      smaller_text = text.substr(0, 
       ((smaller_text.length + text_len_lower)/2)); 
      } 
      else 
      { 
      if (smaller_text.length>=text_len_higher) break; 

      // make larger to the mean of "higher" and this 
      text_len_lower = smaller_text.length; 
      smaller_text = text.substr(0, 
       ((smaller_text.length + text_len_higher)/2)); 
      } 
      temp_item.html(smaller_text); 
      item_width = span_temp_item.width(); 
    } 

... }

+0

ありがとう、私はそれを試してみよう! – novon

1

ことの一つは、それぞれの時間はあなたに何かを追加することである:大体、このような何かを話す

DOMを使用したり、ノード内のhtmlを変更すると、ページが再描画されなければならず、高価な操作になります。ループの外にあるHTML更新を動かすと、処理速度がかなり向上します。

他にも述べたように、$()への呼び出しをループ外に移動することができます。要素への参照を作成し、1800の情報としてループ内のメソッドを呼び出すことができます。

FirebugプラグインでFirefoxを使用している場合は、コードをプロファイリングして最も長い時間がかかっているかどうかを確認することができます。最初のタブの下のプロファイルをクリックして、操作を行い、もう一度プロファイルをクリックしてください。それはあなたのコードの各部分にかかった時間の表を表示します。 jsフレームワークライブラリにある多くのものがリストに表示されます。少しの試行錯誤でそれを分離することもできます。

関連する問題