Я получаю исключение при использовании Thread.спать(x) или ждать()

Я попытался задержать или перевести в спящий режим мою Java-программу, но произошла ошибка.

Я не могу использовать Thread.sleep(x) или wait(). Появляется то же сообщение об ошибке:

несообщаемое исключение java.ленг.InterruptedException; должен быть пойман или объявлен брошенным.

есть ли какой-либо шаг, необходимый перед использованием Thread.sleep() или wait() методами?

13 ответов


у вас впереди много чтения. От ошибок компилятора до обработки исключений, прерываний потоков и потоков. Но это сделает то, что вы хотите:

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

Как говорили другие пользователи, Вы должны окружить свой вызов try{...} catch{...} блок. Но поскольку Java 1.5 был выпущен, есть класс 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


посмотреть на этом отличном кратком посте о том, как сделать это правильно.

по сути: ловить InterruptedException. Помните, что вы должны добавить этот catch-блок. Сообщение объясняет это немного дальше.


используйте следующую конструкцию кодирования для обработки исключений

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

положить Thread.sleep в блоке try catch

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

при использовании 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


попробуйте это:

try{

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

мои способы добавить задержку в программу 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 / Подождите.


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);


  }
}

более простой способ подождать-использовать System.currentTimeMillis(), который возвращает количество миллисекунд с полуночи 1 января 1970 UTC. Например, подождать 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
}

таким образом, вам не нужно возиться с потоками и исключениями. Надеюсь, это поможет!


использовать java.util.concurrent.TimeUnit:

TimeUnit.SECONDS.sleep(1);

спать в течение одной секунды или

TimeUnit.MINUTES.sleep(1);

поспи минутку.

поскольку это цикл, это представляет собой неотъемлемую проблему - дрейф. Каждый раз, когда вы запускаете код, а затем спите, вы будете немного дрейфовать от запуска, скажем, каждую секунду. Если это проблема, то не используйте sleep.

далее sleep не очень гибкими, когда дело доходит до контроля.

для выполнения задачи каждую секунду или в одну секунду задержки я бы сильно рекомендую [ScheduledExecutorService][1] и [scheduleAtFixedRate][2] или [scheduleWithFixedDelay][3].

для запуска метода 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");
}

Thread.sleep() просто для начинающих и может быть подходящим для модульных тестов и доказательств концепции.

но, пожалуйста НЕ использовать sleep() для производства кода. В конце концов sleep() может сильно укусить вас.

рекомендуется для многопоточных / многоядерных приложений java использовать концепцию "ожидание потока". Wait освобождает все блокировки и мониторы, удерживаемые потоком, что позволяет другим потокам приобретать эти мониторы и продолжать работу, пока ваш поток мирно спит.

код ниже демонстрирует эту технику:

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();
        }
    }
}

кроме того, если вы не хотите иметь дело с нитками, попробуйте этот метод:

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

Он начинается, когда вы его вызываете, и заканчивается, когда прошло количество секунд.