

JavaScriptの同期処理と非同期処理についてです。

以下のようなソースの中に2秒ほどスリープする処理を入れたいのですが、うまく行きません。

[code]

    if(hoge){
    　　if(!huga){
    　　　　// ここに2秒スリープ処理
    　　　　location.href = hoge.html;
    　　}
    　　if(hogeType == "a" && hugaType == "b"){
    　　　　location.href = huga.html;
    　　}
    }
    hogefunc(hoge, huga);
    
[/code]

調べると、`setTimeout`関数や`jQuery.Deferred`というものが使えそうだったのですが、`location.href =
hoge.html;`は走らないのですが、`if(hogeType == "a" && hugaType == "b"){`
これより下の処理が走ってしまい困っています。  
どうすればスリープさせることができるのでしょうか？


CC BY-SA 3.0
2016-11-24T09:44:13.537
30649
2016-11-28T13:27:18.307
2016-11-24T15:19:20.143
2238
19702
question
javascript
JavaScriptでスリープ処理を同期的にしたい。


JavaScriptに`sleep(1000)`のようなその行X秒止まる関数はありません（スクリプト実行中はウェブページが固まるのでそのような関数があるとこまる）。  
代わりにコールバック関数を用いる`setTimeout`などがあります。機能としては止まるのではなく、指定秒数後に指定の関数を呼び出す感じです。なので`setTimeout`はほぼ一瞬で実行が終わり、その先が実行されます。  
質問の例ですと以下のような感じでスリープと同じような効果にできます。

[code]

    //スリープが入るかもしれ無い部分のあと全て
    function remaining() {
        if(hoge) {
            if(hogeType == "a" && hugaType == "b") {
                location.href = huga.html;
            }
        }
        hogefunc(hoge, huga);
    }
    
    if(hoge && !huga) { //2秒待つ場合
        setTimeout(function() {
            location.href = hoge.html;
            remaining();
        }, 2000);
    } else { //2秒また無い場合
        remaining();
    }
    
[/code]

やりたいことがわからないので出来るだけそのままに訳しましたが、繰り返しが多いですし読みづらいです。`sleep`ではなくコールバックを意識してアルゴリズムを組めばもう少しましになるとは思います。

* * *

**追記**  
マルチポスト先で以下のようなコードが上がっていますが、 **使わないことを強く勧めます**
。上にも書きましたが、JavaScriptはその仕様上スクリプト実行中はユーザーの入力は一切受け付けれません（ブラウザがへぼいのではなく、HTML,CSS,JS諸々がそういう仕様）。なので、以下のようなコードを入れるとスリープしている間ユーザーは何もできなくなり、とても悪い体験につながります。実質ブラクラみたいなものです。信じられなければ、10秒止めるコードを用意したのでどうぞ:

[code]

    //!!!!!注意!!!!!
    //ページ（場合によってブラウザ全体）が10秒固まります。
    var time = new Date().getTime();
    while (new Date().getTime() < time + 10000);
    console.log("おわり");
[/code]


CC BY-SA 3.0
2016-11-24T16:19:07.147
30659
2016-11-28T13:27:18.307
2016-11-28T13:27:18.307
3974
3974
30649
answer