2011-10-16 8 views
7

次のテストは基本的に〜1000数学演算で、ほとんどのPCやアンドロイドブラウザ、iOS 4.xでうまく動作します。 iOS5 Safari(iPhone 4とiPad 2)では、「JavaScript:エラー未定義のJavaScript実行がタイムアウトを超えました」というメッセージが表示されます。どんな助けでも大変感謝しています。Javascript IOS5「JavaScript実行がタイムアウトを超えました」

/** Converts numeric degrees to radians */ 
if (typeof (Number.prototype.toRad) === "undefined") { 
    Number.prototype.toRad = function() { 
    return this * Math.PI/180; 
    } 
} 

function gc(lat1, lon1, lat2, lon2) { 
    // returns the distance in km between a pair of latitude and longitudes 
    var R = 6371; // km 
    var dLat = (lat2 - lat1).toRad(); 
    var dLon = (lon2 - lon1).toRad(); 
    var a = Math.sin(dLat/2) * Math.sin(dLat/2) + 
     Math.cos(lat1.toRad()) * Math.cos(lat2.toRad()) * 
     Math.sin(dLon/2) * Math.sin(dLon/2); 
    var c = 2 * Math.atan2(Math.sqrt(a), Math.sqrt(1 - a)); 
    var d = R * c; 
    return d; 
} 

function test() { 
    var d1 = new Date(); 
    var lat1, lon1, lat2, lon2; 
    lat1 = -36; 
    lon1 = 174; 

    lat2 = lat1; 
    lon2 = lon1; 

    while (lat2 > -37) { 
    lat2 = lat2 - 0.001; 
    var stest = "lat1=" + lat1 + ",lon1=" + lon1 + ",lat2=" + lat2 + ",lon2=" + lon2 + "=" + gc(lat1, lon1, lat2, lon2); 

    } 
    var d2 = new Date(); 
    var stest = (d2.getTime() - d1.getTime())/1000.0 + "s"; 
    $("#lblTest").html(stest + "<BR/>" + $("#lblTest").html()); 

} 
+0

どの機能でタイムアウトが発生していますか? – Zakaria

+0

こんにちはザカリア私はtest()を呼び出す必要があります。これは、生産コードのエラーをシミュレートするため、gc()を最大1000回呼び出すためです。 – ajayel

答えて

10

javascriptで長時間実行される操作を実行したい場合、一部のブラウザで実行されるスクリプトの実行時間制限に近づいている場合は、関数を複数の部分に分割して1つずつ実行する必要があります非常に短いsetTimeout(fn, 1)を実行し、次の部分などを実行します。このようにすると、他のスクリプトや他のイベントに処理する機会が与えられるので、数時間コードを実行できます。これを行うには、コードの再構成が必要になることがありますが、少しでも作業が可能です。擬似コードで

基本的なコンセプトは、このようになります:あなたの特定のコードで

var state = {}; // set initial state 
var done = false; 

function doWork() { 
    // do one increment of work that will never get even close to the browser 
    // execution time limit 
    // update the state object with our current operating state for the next execution 
    // set done = true when we're done processing 
    if (!done) { 
     setTimeout(doWork, 1); 
    } 
} 

doWork(); 

、あなたはこのような何かを行うことができます。一度に100の緯度ポイントを処理してから、次に100を実行するために短いsetTimeoutを実行するなどです。 100番台の数字は、何が最もうまくいくかを調整できます。数値が高いほど、各タイマーでの実行時間は長くなりますが、実行時間は短縮されますが、ブラウザスクリプトの実行制限に近づくほどです。 setTimeoutメソッドは、(他のイベントを処理して)生きているブラウザを保持し、中に蹴りからの実行時間制限を防ぐことができます。

function test() { 
    var d1 = new Date(); 
    var lat1, lon1, lat2, lon2, done = false;; 
    lat1 = -36; 
    lon1 = 174; 

    lat2 = lat1; 
    lon2 = lon1; 

    function calcGC() { 
     var cntr = 0; 
     while (lat2 > -37 && cntr < 100) { 
      lat2 = lat2 - 0.001; 
      var stest = "lat1=" + lat1 + ",lon1=" + lon1 + ",lat2=" + lat2 + ",lon2=" + lon2 + "=" + gc(lat1, lon1, lat2, lon2); 
      cntr++; 
     } 
     // if we have more to go, then call it again on a timeout 
     if (lat2 > -37) { 
      setTimeout(calcGC, 1); 
     } else { 
      var d2 = new Date(); 
      var stest = (d2.getTime() - d1.getTime())/1000.0 + "s"; 
      $("#lblTest").html(stest + "<BR/>" + $("#lblTest").html()); 
     } 
    } 
    calcGC(); 
} 
+0

この優れた説明例jfriend00では、このページでできるだけ早く試してみます。素晴らしい! – ajayel

+0

が実装され、とてもうまくいきましたjfriend00 – ajayel

1

Appleのようなサウンドは、iOS5のjavascriptの実行タイムアウトを短縮しました。これはおそらく、Mobile Safariの一般的な速度向上と、UIWebViews用のNitroエンジンの搭載によるものです。

+0

確かに私たちのコードはiOS4上で一貫してうまく動作しました – ajayel

4

私の気持ちはIOS5サファリにバグがあることがあり、かつて私は、これらのエラーを取得するために始めましたので、 、Google Mobile Searchのページを含めて全面的にそれらを取得し、タイムアウトやポーズが目につくことはありません。 Safariを強制終了して再起動すると、問題が解決されます(それが再び起きるまで - おそらく、Safariを当初の状態に戻す本物のタイムアウトです)。

マルチタスクメニューからSafariを強制終了して再起動しましたか?

0

私はあまりにもIOS5のブラウザのバグだと思う。私たちも同様の問題を抱えています。私たちにはたくさんのJavascriptコードを持つ大規模なRIAアプリケーションがあり、ページを更新した後、ブラウザはタイムアウト例外をスローし始めます。 iOS4にはこの問題はありませんでした。例外が発生すると、ブラウザが完全に壊れるまで、悪い状態から悪い状態に変わります。他の無関係のページは例外をスローし、レンダリングを拒否します。

Safariを強制終了して再起動すると、問題が解決します。

+0

こんにちはVladHさんとWill Deanさん、私たちのエラーは新鮮なブラウザでも一貫して再現でき、jfriend00sのアプローチで完全に消えてしまいました。興味深いことに、2つのブラウザ(またはフルスクリーンウェブ)ウィンドウが同じコードを同時に実行している場合は、元の質問に記載されているjavascriptエラーが発生します。 – ajayel

+0

@VladH、あなたのアプリでwindow.setTimeoutまたはwindow.setIntervalを使用していますか? – illvm

+0

いいえ、私たちはまだアプリケーションのどこがタイムアウトの原因になっているのかを特定しようとしています。私たちのアプリは広大で非同期性が高いです。しかし、回避策を見つけても、大きな問題があります。これらのタイムアウト・エラーがポップアップすると、Safariが壊れてしまいます.1つはページを数回リフレッシュし、問題のないJSスクリプトは、関連性のないサイトを別々のタブに表示します。私たちのスクリプトはブラウザを破壊するべきではありません。ちょうど、我々はちょうどGoogleマップのサイトで、衛星のレイヤーをオンとオフに切り替えることでこれを再現しました。 – VladH

関連する問題