Pourquoi appeler Thread.currentThread.interrupt () dans un bloc catch InterruptException?

Pourquoi appeler la méthode Thread.currentThread.interrupt () dans le bloc catch?

Ceci est fait pour garder l’état .

Lorsque vous interceptez l’interception et l’ InterruptException , vous empêchez essentiellement les méthodes / groupes de threads de niveau supérieur de détecter l’interruption. Ce qui peut causer des problèmes.

En appelant Thread.currentThread().interrupt() , vous définissez l’indicateur d’interruption du thread, afin que les gestionnaires d’interruption de niveau supérieur le remarquent et puissent le gérer correctement.

La concurrence dans la pratique de Java en discute plus en détail au chapitre 7.1.3: Réagir à une interruption . Sa règle est la suivante:

Seul le code qui implémente la stratégie d’interruption d’un thread peut avaler une demande d’interruption. Les tâches et le code de bibliothèque à usage général ne doivent jamais avaler les demandes d’interruption.

Je pense que cet exemple de code rend les choses un peu claires. La classe qui fait le travail:

  public class InterruptedSleepingThread extends Thread { @Override public void run() { doAPseudoHeavyWeightJob(); } private void doAPseudoHeavyWeightJob() { for (int i=0;i if(Thread.currentThread().isInterrupted()) { System.out.println("Thread interrupted\n Exiting..."); break; }else { sleepBabySleep(); } } } /** * */ protected void sleepBabySleep() { try { Thread.sleep(1000); } catch (InterruptedException e) { //e.printStackTrace(); Thread.currentThread().interrupt(); } } } 

La classe principale:

  public class InterruptedSleepingThreadMain { /** * @param args * @throws InterruptedException */ public static void main(Ssortingng[] args) throws InterruptedException { InterruptedSleepingThread thread = new InterruptedSleepingThread(); thread.start(); //Giving 10 seconds to finish the job. Thread.sleep(10000); //Let me interrupt thread.interrupt(); } } 

Essayez d’appeler une interruption sans rétablir le statut.

Remarque:

http://download.oracle.com/javase/7/docs/technotes/guides/concurrency/threadPrimitiveDeprecation.html

Comment puis-je arrêter un thread qui attend de longues périodes (par exemple, pour la saisie)?

Pour que cette technique fonctionne, il est essentiel que toute méthode qui intercepte une exception d’interruption et ne soit pas prête à y faire face réaffirme immédiatement l’exception. Nous disons réaffirmer plutôt que renvoyer, car il n’est pas toujours possible de renvoyer l’exception. Si la méthode qui intercepte l’exception InterruptedException n’est pas déclarée pour lancer cette exception (cochée), alors elle devrait “se réinterrompre” avec l’incantation suivante:

 Thread.currentThread().interrupt(); 

Cela garantit que le thread relance l’exception InterruptedException dès que possible.

Je considère cela comme une mauvaise pratique ou du moins un peu risquée. Habituellement, les méthodes de haut niveau n’effectuent pas d’opérations de blocage et elles ne verront jamais InterruptedException . Si vous le masquez dans tous les endroits où vous effectuez des opérations interruptibles, vous ne l’obtiendrez jamais.

La seule raison de Thread.currentThread.interrupt() et de ne pas Thread.currentThread.interrupt() d’autre exception ou de demande d’interruption de signalisation (par exemple, définir une variable variable locale interrupted dans la boucle principale d’un thread) est la situation dans laquelle vous ne pouvez vraiment rien faire. l’exception, comme dans les finally blocs.

Voir la réponse de Péter Török, si vous souhaitez mieux comprendre les implications de l’appel Thread.currentThread.interrupt() .