Thread.sleep(x)またはwait()を使用すると例外が発生します


343

Javaプログラムを遅らせようとしたり、スリープさせたりしようとしましたが、エラーが発生しました。

Thread.sleep(x)またはを使用できませんwait()。同じエラーメッセージが表示されます。

報告されていない例外java.lang.InterruptedException; キャッチするか、スローするように宣言する必要があります。

Thread.sleep()またはwait()メソッドを使用する前に必要な手順はありますか?


8
さて、これは人気があります。Javaプログラムを数秒間遅らせる必要がある人は非常に多くいるはずです。想像するのは難しい。もちろん、投稿に正しいタイトルを付けることは非常に役立ちます。
Robert Harvey

回答:


575

あなたはあなたの前にたくさんの読書があります。コンパイラエラーから、例外処理、スレッド化、スレッド割り込みまで。しかし、これはあなたが望むことをします:

try {
    Thread.sleep(1000);                 //1000 milliseconds is one second.
} catch(InterruptedException ex) {
    Thread.currentThread().interrupt();
}

1
あなたの助けに感謝、私にそれを実行することができ..横に、キャッチのための使用は何である(例外:InterruptedException EX)
ヴィンセント低

4
Abelからの返信を参照してください。Google for InterruptedException。長い話を短くすると、スレッドはスリープ中に中断される可能性があり、これは一種の例外であり、明示的に処理する必要があります。
Konrad Garus

8
いくつかの答えは例外に対して何もしないように指示し、いくつかはスローするように言い、これはinterrupt()に指示します。誰かが適切である理由とその理由について話し合う必要がありますか?
スマ

6
@Sumaスタックオーバーフロー自体を含む、それに関する多くの議論があります。検索するだけです。コメントするには長すぎます。数年後、私が持っている唯一の答えは、次のとおりです。通常、理想的なソリューションは、スレッドが正常に実行しているものをすべて終了することです(このトランザクションのロールバック、ループの中断など)が、これはコンテキストに大きく依存します。
Konrad Garus 2013年

タイマーって何ですか?タイマーで同じ機能を実現できますか?私はjavaのドキュメントを読んで、遅延について何かを述べましたが、高校のプログラミングの2年目を終えようとしているのですが、それについて話している遅延がここで役立つのか、それとも適切なクラス
Ungeheuer 2015年

195

他のユーザーが言ったように、あなたの呼び出しをtry{...} catch{...}ブロックで囲むべきです。しかし、Java 1.5がリリースされて以来、Thread.sleep(millis)と同じことをするTimeUnitクラスがありますが、より便利です。スリープ操作の時間単位を選択できます。

try {
    TimeUnit.NANOSECONDS.sleep(100);
    TimeUnit.MICROSECONDS.sleep(100);
    TimeUnit.MILLISECONDS.sleep(100);
    TimeUnit.SECONDS.sleep(100);
    TimeUnit.MINUTES.sleep(100);
    TimeUnit.HOURS.sleep(100);
    TimeUnit.DAYS.sleep(100);
} catch (InterruptedException e) {
    //Handle exception
}

また、追加のメソッドがあります: TimeUnit Oracle Documentation


6
これらの呼び出しを必要なtry-catch例外処理で囲む方法の例については、他の回答を参照してください。
バジルブルク2013年

2
「import java.util.concurrent.TimeUnit;」を忘れないでください。
コーダー


13

次のコーディング構成を使用して例外を処理します

try {
  Thread.sleep(1000);
} catch (InterruptedException ie) {
    //Handle exception
}

8

あなたThread.sleepをトライキャッチブロックに入れてください

try {
    //thread to sleep for the specified number of milliseconds
    Thread.sleep(100);
} catch ( java.lang.InterruptedException ie) {
    System.out.println(ie);
}

7

Androidを使用するとき(私がJavaを使用するのはこのときだけです)、スレッドをスリープさせる代わりにハンドラーを使用することをお勧めします。

final Handler handler = new Handler();
    handler.postDelayed(new Runnable() {
        @Override
        public void run() {
            Log.i(TAG, "I've waited for two hole seconds to show this!");

        }
    }, 2000);

リファレンス:http : //developer.android.com/reference/android/os/Handler.html


4
これはAndroid向けで、コアJavaではありません
ガネーシュクリシュナン2016年

3

これを試して:

try{

    Thread.sleep(100);
}catch(Exception e)
{
   System.out.println("Exception caught");
}

8
ExceptionJavaで捕まえるのは悪い習慣ではないでしょうか?
マイケルドースト2014

2
ここでの他の回答と同様に、InterruptedExceptionをより
適切に

5
これは「ポケモン例外ハンドラ」と呼ばれ、すべてをキャッチする必要があります。
James Tayler、2016

3

Javaプログラムに遅延を追加する私の方法。

public void pause1(long sleeptime) {
    try {
        Thread.sleep(sleeptime);
    } catch (InterruptedException ex) {
        //ToCatchOrNot
    }
}

public void pause2(long sleeptime) {
    Object obj = new Object();
    if (sleeptime > 0) {
        synchronized (obj) {
            try {
                obj.wait(sleeptime);
            } catch (InterruptedException ex) {
                //ToCatchOrNot
            }
        }
    }
}
public void pause3(long sleeptime) {
    expectedtime = System.currentTimeMillis() + sleeptime;
    while (System.currentTimeMillis() < expectedtime) {
        //Empty Loop   
    }
}

これは順次遅延ですが、ループ遅延についてはJavaの遅延/待機を参照してください


ここでは露骨な自己宣伝は禁止されています。ヘルプセンターの最後のポイントをご覧ください。ただし、リンクをプロフィールに追加することはできます-許可されています。
SLバース-モニカを2015年

3
public static void main(String[] args) throws InterruptedException {
  //type code


  short z=1000;
  Thread.sleep(z);/*will provide 1 second delay. alter data type of z or value of z for longer delays required */

  //type code
}

例えば:-

class TypeCasting {

  public static void main(String[] args) throws InterruptedException {
    short f = 1;
    int a = 123687889;
    short b = 2;
    long c = 4567;
    long d=45;
    short z=1000;
    System.out.println("Value of a,b and c are\n" + a + "\n" + b + "\n" + c + "respectively");
    c = a;
    b = (short) c;
    System.out.println("Typecasting...........");
    Thread.sleep(z);
    System.out.println("Value of B after Typecasting" + b);
    System.out.println("Value of A is" + a);


  }
}

0

待機する簡単な方法は、を使用することですSystem.currentTimeMillis()。これは、UTC 1970年1月1日の午前0時からのミリ秒数を返します。たとえば、5秒待つには:

public static void main(String[] args) {
    //some code
    long original = System.currentTimeMillis();
    while (true) {
        if (System.currentTimeMillis - original >= 5000) {
            break;
        }
    }
    //more code after waiting
}

この方法では、スレッドや例外をいじる必要はありません。お役に立てれば!


これは待機中にCPUを消費します。
yacc 2017年

@yaccこれは事実ですが、スレッドを使用するよりも簡単で、CPUをあまり使用しません。
サム

0

使用java.util.concurrent.TimeUnit

TimeUnit.SECONDS.sleep(1);

1秒間寝るか

TimeUnit.MINUTES.sleep(1);

少し寝ます。

これはループであるため、ドリフトという固有の問題があります。コードを実行してからスリープするたびに、たとえば毎秒実行から少しドリフトします。これが問題である場合は、使用しないでくださいsleep

さらに、sleepコントロールに関しては、それほど柔軟ではありません。

1秒ごとまたは1秒の遅延でタスクを実行するには、[ ] [1]と[ ] [2]または[ ] [3]のいずれかを強くお勧めします。ScheduledExecutorServicescheduleAtFixedRatescheduleWithFixedDelay

メソッドをmyTask毎秒実行するには(Java 8):

public static void main(String[] args) {
    final ScheduledExecutorService executorService = Executors.newSingleThreadScheduledExecutor();
    executorService.scheduleAtFixedRate(App::myTask, 0, 1, TimeUnit.SECONDS);
}

private static void myTask() {
    System.out.println("Running");
}

0

Thread.sleep() 初心者にとっては簡単で、単体テストや概念実証に適している場合があります。

ただし、量産コードには使用しないでくださいsleep()。最終的にsleep()はあなたをひどく噛むかもしれません。

マルチスレッド/マルチコアJavaアプリケーションが「スレッド待機」の概念を使用するためのベストプラクティス。待機は、スレッドによって保持されているすべてのロックとモニターを解放します。これにより、他のスレッドがそれらのモニターを取得して、スレッドが平和にスリープしている間に続行できます。

以下のコードはその手法を示しています。

import java.util.concurrent.TimeUnit;
public class DelaySample {
    public static void main(String[] args) {
       DelayUtil d = new DelayUtil();
       System.out.println("started:"+ new Date());
       d.delay(500);
       System.out.println("half second after:"+ new Date());
       d.delay(1, TimeUnit.MINUTES); 
       System.out.println("1 minute after:"+ new Date());
    }
}

DelayUtil 実装:

import java.util.concurrent.TimeUnit;
import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.ReentrantLock;

public class DelayUtil {
    /** 
    *  Delays the current thread execution. 
    *  The thread loses ownership of any monitors. 
    *  Quits immediately if the thread is interrupted
    *  
    * @param durationInMillis the time duration in milliseconds
    */
   public void delay(final long durationInMillis) {
      delay(durationInMillis, TimeUnit.MILLISECONDS);
   }

   /** 
    * @param duration the time duration in the given {@code sourceUnit}
    * @param unit
    */
    public void delay(final long duration, final TimeUnit unit) {
        long currentTime = System.currentTimeMillis();
        long deadline = currentTime+unit.toMillis(duration);
        ReentrantLock lock = new ReentrantLock();
        Condition waitCondition = lock.newCondition();

        while ((deadline-currentTime)>0) {
            try {
                lock.lockInterruptibly();    
                waitCondition.await(deadline-currentTime, TimeUnit.MILLISECONDS);
            } catch (InterruptedException e) {
                Thread.currentThread().interrupt();
                return;
            } finally {
                lock.unlock();
            }
            currentTime = System.currentTimeMillis();
        }
    }
}

-2

または、スレッドを処理したくない場合は、次の方法を試してください。

public static void pause(int seconds){
    Date start = new Date();
    Date end = new Date();
    while(end.getTime() - start.getTime() < seconds * 1000){
        end = new Date();
    }
}

呼び出すと開始し、秒数が経過すると終了します。


7
これは、スリープ時間中にCPUを消費します。Thread.sleep()では、スレッドをスケジュール解除できます。
Vivek Pandey 2013年

あなたはリディであり、水はありません:D
M410

17
user2276378は質問の英語を誤解していた。OPは、ユーザー2276378が「スリープまたは待機を使用できなかった」と述べ、それらを使用できない(または使用を許可されなかった)と考え、スリープまたは待機を使用しない有効なソリューションを提供しました。厳しすぎる英語にならないように心がけましょう。
David Newcomb 2014年
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.