Как убить java.lang.Thread
в Java?
См. эту тему Sun о том, почему они устарели Thread.stop()
. В ней подробно рассказывается о том, почему этот метод был плохим, и что следует сделать для безопасной остановки потоков в целом.
Рекомендуемый способ - использовать общую переменную в качестве флага, который запрашивает остановку фонового потока. Затем эта переменная может быть установлена другим объектом, запрашивающим завершение потока.
Как правило, вы не...
Вы просите его прервать то, что он делает, используя Thread.interrupt() (ссылка на javadoc).
Хорошее объяснение причин этого находится в javadoc здесь (ссылка на java technote).
В Java потоки не убил, но мешает какой-нить делается в сотрудничество. Нить просят расторгнуть и затем нить аккуратно завершить работу.
Часто поля летучих логическое
используется, что поток периодически проверяет и заканчивается, когда он установлен на соответствующее значение.
Я не использовать логическое
, чтобы проверить, является ли поток должен прекратить. Если вы используете летучих
в поле модификатора, это будет работать надежно, но если ваш код становится более сложным, а использует другие методы блокирования внутри а
цикл, это может произойти, что ваш код будет не прекращает или хотя бы дольше как вы, возможно, захотите.
определенные методы блокирования библиотека поддерживает прерывание.
Каждый поток имеет уже логический флаг прерванное состояние, и вы должны использовать его. Он может быть реализован следующим образом:
public void run() {
try {
while (!interrupted()) {
// ...
}
} catch (InterruptedException consumed)
/* Allow thread to exit */
}
}
public void cancel() { interrupt(); }
Исходный код адаптирован из в Java параллелизм на практике. Поскольку отменить()` метод общедоступен, вы можете позволить другому потоку вызвать этот метод, как вы хотели.
Один из способов - установить переменную класса и использовать ее в качестве дозорного.
Class Outer {
public static volatile flag = true;
Outer() {
new Test().start();
}
class Test extends Thread {
public void run() {
while (Outer.flag) {
//do stuff here
}
}
}
}
Установите внешнюю переменную класса, т.е. flag = true в приведенном выше примере. Установите ее в false, чтобы 'убить' поток.
Есть способ как это можно сделать. Но если вы должны были использовать его, либо вы плохой программист или вы используете код, написанный плохим программистам. Таким образом, вы должны думать о том, чтобы остановить плохой программист или остановить, используя этот плохой код. Это решение только для ситуаций, когда нет другого пути.
Thread f = <A thread to be stopped>
Method m = Thread.class.getDeclaredMethod( "stop0" , new Class[]{Object.class} );
m.setAccessible( true );
m.invoke( f , new ThreadDeath() );
Я хочу добавить несколько наблюдений, на основе замечаний, которые накопились.
Я'd не будем голосовать за нить.стоп()`.
Как, например, у вас продолжительная операция (как сетевой запрос). Якобы вы ждете ответа, но это может занять некоторое время и пользователь перешел на другой интерфейс. Этой теме ждем теперь А) бесполезно б) потенциальная проблема, потому что, когда он получит результат, он's полностью бесполезны и он будет вызывать обратные вызовы, что может привести к ряду ошибок.
Все это и он может сделать обработки ответа, которая может быть интенсивной нагрузке. И вы, как разработчик, не могу даже остановить его, потому что вы можете'т бросить если (нить.currentThread().isInterrupted())
в ВСЕ код.
Так что отсутствие возможности принудительно остановить поток странно.
Вопрос является довольно расплывчатым. Если вы имели в виду “как мне написать программу, так что поток останавливается, когда я захочу”, то различные другие ответы должны быть полезными. Но если вы имели в виду “у меня проблема с серверов я не могу Перезагрузить сейчас и мне просто нужно конкретное потока, чтобы умереть, что бы то ни стало”, тогда вам нужен инструмент вмешательства в матч инструментов мониторинга как jstack
.
Для этой цели я создал jkillthread. Увидеть его инструкция по применению.
Есть конечно случае, когда вы запускаете какую-то не-полностью доверенным кодом. (Я лично этого загруженные скрипты в моей среде Java. Да, есть охранная сигнализация колокольный звон повсюду, но это's частью приложения.) В этом прискорбном случае вы в первую очередь просто надеюсь, задавая авторы сценария в отношении какой-то логический пуск/Дон'т-сигнал. Свой единственный приличный не безопасно вызвать метод Stop-нить, если, скажем, он работает дольше, чем некоторые ожидания.
Но, это только на "достойную", и не абсолютный, потому что код может перехватить ошибку ThreadDeath (или как исключение явно бросать), и не выдали его как-нить по-джентльменски должен делать. Так, нижняя линия АФАЙЯ нет абсолютной безаварийности.
Нет никакого способа, чтобы корректно убить поток.
Вы можете попробовать, чтобы прервать нить, одна стратегия общин намерена использовать "ядовитую пилюлю" для сообщений потока, чтобы остановить себя
public class CancelSupport {
public static class CommandExecutor implements Runnable {
private BlockingQueue<String> queue;
public static final String POISON_PILL = “stopnow”;
public CommandExecutor(BlockingQueue<String> queue) {
this.queue=queue;
}
@Override
public void run() {
boolean stop=false;
while(!stop) {
try {
String command=queue.take();
if(POISON_PILL.equals(command)) {
stop=true;
} else {
// do command
System.out.println(command);
}
} catch (InterruptedException e) {
stop=true;
}
}
System.out.println(“Stopping execution”);
}
}
}
BlockingQueue<String> queue=new LinkedBlockingQueue<String>();
Thread t=new Thread(new CommandExecutor(queue));
queue.put(“hello”);
queue.put(“world”);
t.start();
Thread.sleep(1000);
queue.put(“stopnow”);
Как правило, вы не'т убить, остановить или прервать нить (или проверить ли она прервана()), но пусть это прекратить, естественно.
Это просто. Вы можете использовать любую петлю вместе с (летучие) логическая переменная внутри метода Run() для контроля резьбы'ы деятельность. Вы также можете вернуться от активного потока в основной поток, чтобы остановить его.
Таким образом, вы корректно убить поток :) .
Попытки резкого прекращения потока хорошо известны плохой практикой программирования и свидетельствует о плохой дизайн приложения. Все потоки многопоточного приложения прямо и косвенно разделяют те же состояния процесса и вынуждены сотрудничать друг с другом, чтобы держать его в соответствие, в противном случае ваша заявка будет подвержен ошибки, которые очень трудно диагностировать. Таким образом, это обязанность застройщика предоставлять гарантии такой последовательности через тщательный и понятный дизайн приложения.
Существует два основных решения для управляемого прерывания потоков:
Хорошее и подробное объяснение проблемы, связанные с резким прекращением потоков, а также примеры неправильных и правильных решений для контролируемого прекращения потоков могут быть найдены здесь:
Я не'т получить прерываний для работы в Android, поэтому я использовала этот метод, прекрасно работает:
boolean shouldCheckUpdates = true;
private void startupCheckForUpdatesEveryFewSeconds() {
Thread t = new Thread(new CheckUpdates());
t.start();
}
private class CheckUpdates implements Runnable{
public void run() {
while (shouldCheckUpdates){
//Thread sleep 3 seconds
System.out.println("Do your thing here");
}
}
}
public void stop(){
shouldCheckUpdates = false;
}
'убийство резьба' это не правильное слово, чтобы использовать. Вот один из способов, которые мы можем реализовать грациозно завершения/выхода из потока будет:
Интерфейс Runnable, который я использовал:
`` TaskThread класс реализует интерфейс Runnable {
логическое shouldStop;
общественные TaskThread(логическое shouldStop) { это.shouldStop = shouldStop; }
@Переопределить общественного недействительными Run() {
Системы.из.метод println("какая-нить началась с");
хотя (!shouldStop) { // что-то делать }
Системы.из.метод println (на"поток закончился и");
}
общественного недействительными стоп() { shouldStop = истина; }
} ``
Пусковым класс:
`` ThreadStop общественных класса {
общественности статической силы основных(string[] аргументы) {
Системы.из.метод println (и"Начать и");
// Запустить поток Задача TaskThread = новый TaskThread(ложь); Поток T = новый поток(задача); Т.начать();
// Остановить поток задач.стоп();
Системы.из.код println (на"конце" - а);
}
} ``