首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Java Thread.interrupted和中断标志

Java Thread.interrupted和中断标志
EN

Stack Overflow用户
提问于 2017-05-12 15:51:01
回答 1查看 2.6K关注 0票数 2

我正在学习关于Java并发性的教程。在链接的文章中提供了一个关于Thread.interrupted实现的片段。

中断机制是使用称为中断状态的内部标志来实现的。调用Thread.interrupt设置此标志。当线程通过调用静态方法Thread.interrupted来检查中断时,中断状态将被清除。一个线程用于查询另一个线程的中断状态的非静态isInterrupted方法不会更改中断状态标志。按照约定,任何通过抛出InterruptedException退出的方法都会清除中断状态。但是,中断状态总是有可能通过另一个调用中断的线程立即重新设置。

这是对应的Javadoc

java.lang.Thread public static boolean interrupted()测试当前线程是否已被中断。此方法将清除线程的中断状态。换句话说,如果连续两次调用此方法,则第二个调用将返回false (除非当前线程再次中断,在第一次调用清除其中断状态之后,在第二次调用检查该线程之前)。由于线程在中断时未激活而忽略的线程中断将由此方法反映,该方法返回false。返回:如果当前线程被中断,则为true;否则为false。另见:isInterrupted()

在阅读了这两种关于Thread.interrupted的解释之后,我对中断标志是什么以及它在哪里被清除感到困惑。像Thread.interrupted这样的函数不应该是幂等函数,而不应该修改被调用对象的状态吗?我知道Thread.interrupted是静态的,因为它在currentThread()上操作,而Thread.isInterrupted是一个实例方法,因为它对正在调用的Thread实例进行操作。

EN

回答 1

Stack Overflow用户

发布于 2018-03-06 03:21:57

有两种不同的检查中断标志状态的方法。不幸的是,你应该使用的那个看起来不像你不该使用的那样方便。

您不应该使用的是Thread#interrupted,因为它重置标志。我认为中断()是一种非常简单的方法,在这种情况下,您希望检测中断,如果被中断,则清除标志并抛出InterruptedException:

代码语言:javascript
复制
if (Thread.interrupted()) {
    throw new InterruptedException();

当抛出InterruptedException时,应该清除中断标志,因此在这种情况下,这样做很方便。除非您正在做这样的事情(这应该是非常罕见的),永远不要使用这种方法。

您应该使用的方法是Thread#isInterrupted。它通常使用当前运行的线程调用,如

代码语言:javascript
复制
Thread.currentThread().isInterrupted()

此方法不会更改中断标志的状态,而且无论何时要检查是否中断,都应该使用该方法。

请注意,中断是一个静态方法,它总是检查当前线程的中断状态,而isInterrupted是一个实例方法,因此您必须查找当前线程才能调用该方法(或者您可以测试其他线程的中断状态)。

使中断更容易使用已经导致更容易出错的代码,因为人们采取更容易的方法,而不读取api文档。

票数 3
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/43941832

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档