Скопируйте код кода следующим образом:
// Начать поток
общественный недействительный старт ();
общественный недействительный запуск ();
// Приостанавливаем и пробуждаем потоки
public void резюме( ); // Не рекомендуется использовать
public void suspend() // Не рекомендуется использовать
общественный статический пустотный сон (длинный миллис);
public static void Sleep(long millis, int nanos);
// Завершить поток
public void stop() // Не рекомендуется использовать
публичное недействительное прерывание ();
// Получаем статус потока
общедоступное логическое значение isAlive();
общедоступное логическое значение isInterrupted( );
общедоступное статическое логическое значение прерывается ();
// метод соединения
public void join() выдает InterruptedException;
1. Создание и запуск потоков
Поток не выполняет код метода run сразу после его установления, а находится в состоянии ожидания. Когда поток находится в состоянии ожидания, вы можете установить различные атрибуты потока с помощью методов класса Thread, такие как приоритет потока (setPriority), имя потока (setName) и тип потока (setDaemon).
Когда вызывается метод start, поток начинает выполнение кода в методе run. Поток переходит в рабочее состояние. Вы можете использовать метод isAlive класса Thread, чтобы определить, запущен ли поток. Когда поток находится в состоянии выполнения, isAlive возвращает true. Когда isAlive возвращает false, поток может находиться в состоянии ожидания или в состоянии остановки. Следующий код демонстрирует переключение между тремя состояниями создания потока, запуска и остановки, а также выводит соответствующее возвращаемое значение isAlive.
Скопируйте код кода следующим образом:
пакет глава2;
общедоступный класс LifeCycle расширяет поток
{
публичный недействительный запуск()
{
интервал п = 0;
в то время как ((++n) < 1000);
}
public static void main(String[] args) выдает исключение
{
LifeCycle thread1 = новый LifeCycle();
System.out.println("isAlive: " + thread1.isAlive());
поток1.start();
System.out.println("isAlive: " + thread1.isAlive());
thread1.join(); // Дождитесь завершения потока thread1, прежде чем продолжить выполнение
System.out.println("поток1 завершился!");
System.out.println("isAlive: " + thread1.isAlive());
}
}
Обратите внимание, что в приведенном выше коде используется метод join. Основная функция этого метода — обеспечить продолжение работы программы после завершения метода запуска потока. Этот метод будет представлен в следующей статье.
Результат выполнения приведенного выше кода:
isAlive: ложь
isAlive: правда
тред1 завершился!
isAlive: ложь
2. Приостановить и активировать потоки
Как только поток начнет выполнять метод run, он не завершится до тех пор, пока метод run не будет завершен. Однако во время выполнения потока вы можете временно остановить выполнение потока двумя способами. Эти два метода — приостановка и сон. После использования suspend для приостановки потока вы можете разбудить его с помощью метода возобновления. После использования режима сна для перевода потока в спящий режим поток может находиться в состоянии готовности только по истечении установленного времени (после завершения режима сна поток может не выполняться немедленно, а только переходит в состояние готовности, ожидая, пока система запланирует выполнение). .
Хотя приостановка и возобновление могут легко приостанавливать и активировать потоки, использование этих двух методов может привести к некоторым непредсказуемым событиям. Поэтому эти два метода помечены как устаревшие (протест), что указывает на то, что эти два метода могут быть удалены в будущем jdk. версий, поэтому старайтесь не использовать эти два метода для работы с потоками. Следующий код демонстрирует использование методов сна, приостановки и возобновления.
Скопируйте код кода следующим образом:
пакет глава2;
публичный класс MyThread расширяет поток
{
класс SleepThread расширяет поток
{
публичный недействительный запуск()
{
пытаться
{
сон (2000);
}
поймать (Исключение e)
{
}
}
}
публичный недействительный запуск()
{
пока (правда)
System.out.println(новый java.util.Date().getTime());
}
public static void main(String[] args) выдает исключение
{
Поток MyThread = новый MyThread();
SleepThread SleepThread = thread.new SleepThread();
SleepThread.start(); // Запускаем поток SleepThread
SleepThread.join(); // Задержка потока SleepThread на 2 секунды
поток.start();
логический флаг = ложь;
пока (правда)
{
Sleep(5000); // Задержка основного потока на 5 секунд;
флаг = !флаг;
если (флаг)
поток.приостановить();
еще
поток.резюме();
}
}
}
На первый взгляд, эффекты от использования сна и приостановки аналогичны, но метод сна не эквивалентен приостановке. Самая большая разница между ними заключается в том, что вы можете приостановить другой поток в одном потоке с помощью метода suspend. Например, в приведенном выше коде поток потока приостанавливается в основном потоке. Sleep работает только в текущем выполняющемся потоке. В приведенном выше коде SleepThread и основной поток находятся в режиме ожидания 2 секунды и 5 секунд соответственно. При использовании режима сна имейте в виду, что вы не можете приостановить один поток в другом потоке. Например, использование метода thread.sleep(2000) в основном методе не может перевести поток в спящий режим на 2 секунды, но может перевести основной поток в спящий режим только на 2 секунды.
При использовании метода сна следует учитывать два момента:
1. Метод сна имеет две перегруженные формы. Одна из перегруженных форм может задавать не только миллисекунды, но и наносекунды (1 000 000 наносекунд равны 1 миллисекунде). Однако виртуальная машина Java на большинстве платформ операционных систем не имеет точности до наносекунд. Поэтому, если для режима сна установлены наносекунды, виртуальная машина Java будет использовать миллисекунду, наиболее близкую к этому значению.
2. При использовании метода сна необходимо использовать броски или try{...}catch{...}. Поскольку метод run не может использовать throws, вы можете использовать только try{...}catch{...}. Когда поток находится в спящем режиме и для прерывания потока используется метод прерывания (этот метод будет обсуждаться в разделе 2.3.3), режим сна выдаст InterruptedException. Метод сна определяется следующим образом:
Скопируйте код кода следующим образом:
public static void Sleep (длинный миллис) выдает InterruptedException
public static void Sleep(long millis, int nanos) выдает InterruptedException
3. Три способа завершить поток
Есть три способа завершить поток.
1. Используйте флаг выхода, чтобы обеспечить нормальное завершение потока, то есть поток завершается после завершения метода запуска.
2. Используйте метод stop для принудительного завершения потока (этот метод не рекомендуется, поскольку остановка, как и приостановка и возобновление, также может привести к непредсказуемым результатам).
3. Используйте метод прерывания, чтобы прервать поток.
1. Завершите поток, используя флаг выхода.
Когда метод run будет выполнен, поток завершится. Но иногда метод run никогда не заканчивается. Например, потоки используются в серверных программах для мониторинга клиентских запросов или других задач, требующих циклической обработки. В этом случае эти задачи обычно помещаются в цикл, например цикл while. Если вы хотите, чтобы цикл выполнялся вечно, вы можете использовать while(true){...} для его обработки. Но если вы хотите, чтобы цикл while завершился при определенных условиях, самый прямой способ — установить флаг логического типа и установить для этого флага значение true или false, чтобы контролировать, будет ли завершаться цикл while. Ниже приведен пример завершения потока с использованием флага выхода.
Скопируйте код кода следующим образом:
пакет глава2;
публичный класс ThreadFlag расширяет поток
{
общедоступный изменчивый логический выход = ложь;
публичный недействительный запуск()
{
пока (!выход);
}
public static void main(String[] args) выдает исключение
{
Поток ThreadFlag = новый ThreadFlag();
поток.start();
Sleep(5000); //Основной поток задерживается на 5 секунд
thread.exit = true // Завершить поток
поток.join();
System.out.println("Тема закрыта!");
}
}
Флаг выхода, выход, определен в приведенном выше коде. Если выход имеет значение true, цикл while завершается, а значение выхода по умолчанию — ложь. При определении выхода используется ключевое слово Java Volatible. Целью этого ключевого слова является синхронизация выхода, что означает, что только один поток может изменять значение выхода одновременно.
2. Используйте метод остановки, чтобы завершить поток.
Используйте метод stop, чтобы принудительно завершить работающий или приостановленный поток. Мы можем использовать следующий код для завершения потока:
поток.стоп();
Хотя использование приведенного выше кода может завершить поток, использование метода остановки очень опасно. Так же, как внезапное отключение питания компьютера вместо завершения работы в соответствии с обычной процедурой, оно может привести к непредсказуемым результатам. Поэтому его не рекомендуется использовать. метод остановки. Завершить поток.
3. Используйте метод прерывания для завершения потока.
Использование метода прерывания для завершения потока можно разделить на две ситуации:
(1) Поток находится в заблокированном состоянии, например, при использовании метода сна.
(2) Используйте while(!isInterrupted()){...}, чтобы определить, прерван ли поток.
В первом случае при использовании метода прерывания метод сна выдаст исключение InterruptedException, а во втором случае поток завершится напрямую. Код ниже демонстрирует использование метода прерывания в первом случае.
Скопируйте код кода следующим образом:
пакет глава2;
публичный класс ThreadInterrupt расширяет поток
{
публичный недействительный запуск()
{
пытаться
{
Sleep(50000); // задержка 50 секунд;
}
улов (InterruptedException e)
{
System.out.println(e.getMessage());
}
}
public static void main(String[] args) выдает исключение
{
Поток потока = новый ThreadInterrupt();
поток.start();
System.out.println("Нажмите любую клавишу в течение 50 секунд, чтобы прервать поток!");
Система.в.чтение();
поток.прерывание();
поток.join();
System.out.println("Поток завершился!");
}
}
Результаты запуска приведенного выше кода следующие:
Скопируйте код кода следующим образом:
Нажмите любую клавишу в течение 50 секунд, чтобы прервать поток!
сон прерван
Ветка закрыта!
После вызова метода прерывания метод сна выдает исключение, а затем выводит сообщение об ошибке: сон прерван.
Примечание. В классе Thread есть два метода, позволяющие определить, завершен ли поток с помощью метода прерывания. Одним из них является статический метод прерывания(), а другим — нестатический метод isInterrupted(). Разница между этими двумя методами заключается в том, что прерывание используется для определения того, прерван ли текущий поток, а метод isInterrupted может использоваться для определения того, был ли прерван текущий поток. другие потоки прерываются. Поэтому while (!isInterrupted()) также можно заменить на while (!Thread.interrupted()).