Как поток должен закрывать себя в Java?

select (с набором маски чтения) вернется с указателем на маркер, но если вы используете ioctl * для проверки количества байтов, ожидающих чтения, оно будет равно нулю. Это признак того, что сокет был отключен.

Это отличная дискуссия по различным методам проверки того, что клиент отключился: Стивен Клири, обнаружение полуоткрытых (отброшенных) соединений .

* для Windows использовать ioctlsocket.

64
задан Roman 22 March 2010 в 10:57
поделиться

4 ответа

Если вы хотите завершить поток, то достаточно просто вернуться. Вам НЕ нужно вызывать Thread.currentThread().interrupt() (хотя это не сделает ничего плохого. Просто это не нужно). Это потому, что interrupt() в основном используется для уведомления владельца потока (ну, не на 100% точно, но вроде того). Поскольку вы являетесь владельцем потока и решили его завершить, уведомлять некого, поэтому вам не нужно его вызывать.

Кстати, почему в первом случае нам нужно использовать currentThread? Разве Thread не ссылается на текущий поток?

Да, не ссылается. Я думаю, это может сбить с толку, потому что, например, Thread.sleep() влияет на текущий поток, но Thread.sleep() - это статический метод.

Если вы НЕ являетесь владельцем потока (например, если вы не расширили Thread и не создали Runnable и т.д.), вы должны сделать

Thread.currentThread().interrupt();
return;

Таким образом, любой код, вызвавший ваш runnable, будет знать, что поток прерван = (обычно) он должен прекратить все свои действия и завершиться. Как я уже говорил, это всего лишь механизм коммуникации. Владелец может просто игнорировать прерванный статус и ничего не делать... но если вы установите прерванный статус, кто-то может поблагодарить вас за это в будущем.

По той же причине вы никогда не должны делать

Catch(InterruptedException ie){
     //ignore
}

Потому что если вы это сделаете, вы остановите сообщение на этом месте. Вместо этого следует сделать

Catch(InterruptedException ie){
    Thread.currentThread().interrupt();//preserve the message
    return;//Stop doing whatever I am doing and terminate
}
65
ответ дан 24 November 2019 в 15:29
поделиться

Если метод run завершается, поток завершается.

Если вы используете цикл, правильный способ выглядит следующим образом:

// In your imlemented Runnable class:
private volatile boolean running = true;

public void run()
{
   while (running)
   {
      ...
   }
}


public void stopRunning()
{
    running = false;
}

Конечно, возврат - лучший способ.

18
ответ дан 24 November 2019 в 15:29
поделиться

Thread - это класс, а не экземпляр; currentThread () - статический метод, который возвращает экземпляр Thread, соответствующий вызывающему потоку.

Используйте (2). interrupt () для нормального использования немного жестока.

1
ответ дан 24 November 2019 в 15:29
поделиться

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

Причина, по которой вам нужно использовать Thread.currentThread () для вызова interrupt () , заключается в том, что interrupt () является методом экземпляра - вы необходимо вызвать его в потоке, который вы хотите прервать, который в вашем случае является текущим потоком. Обратите внимание, что прерывание будет замечено только в следующий раз, когда поток будет заблокирован (например, для ввода-вывода или для монитора) в любом случае - это не означает, что исключение будет сгенерировано немедленно.

5
ответ дан 24 November 2019 в 15:29
поделиться
Другие вопросы по тегам:

Похожие вопросы: