繁体   English   中英

OCJP转储线程同步方法

[英]OCJP Dumps Thread Synchronized Method

嗨,我正在处理SCJP转储,但现在遇到了问题。 这是问题:

void waitForSignal(){
   Object obj = new Object();
   synchronized(Thread.currentThread()){
       obj.wait();
       obj.notify();
   }
}

哪个论述是对的?

答:此代码可以引发InterruptedException

B.这段代码会抛出一个非法的MonitorStateException

C.此代码可以在十分钟后引发TimeoutException

D.颠倒obj.wait()和obj.notify()的顺序可能会导致此方法正常完成

E.从另一个线程调用notify()或notifyAll()可能导致此方法正常完成

F.除非将“ obj.wait()”替换为“((Thread)obj).wait()”,否则不会编译此代码。

我发现在一个转储文件中答案是A,而在另一个转储文件中答案是B。任何人都可以找到正确的答案并为我提供解释吗?

绝对B在这里是正确的。 请参阅IllegalMonitorStateException的API文档:

抛出该异常指示线程试图在对象的监视器上等待,或者通知其他线程在对象监视器上等待而没有拥有指定的监视器。

所获取的监视器是当前线程(顺便说一下,API文档警告不要这样做)。 在obj上调用了wait和notify方法,该方法应该在当前线程对象上调用。

答:Object#wait可以引发InterruptedException。 语言规范说:是否会发生这种情况取决于实现方式:

令线程t为在对象m上执行wait方法的线程,令n为t对m进行的,未与解锁动作匹配的锁定动作的数量。 发生以下操作之一:

  • 如果n为零(即线程t尚未拥有对目标m的锁定),则将引发IllegalMonitorStateException。

  • 如果这是定时等待,并且nanosecs参数不在0-999999范围内,或者millisecs参数为负,则抛出IllegalArgumentException。

  • 如果线程t被中断,则抛出InterruptedException,并且t的中断状态设置为false。

  • 否则,将发生以下顺序:(...)

因此,没有严格定义将首先检查哪些情况。 实际上,在Oracle或IBM JDK中不会抛出InterruptedException,而在IllegalMonitorStateException中会抛出InterruptedException。

但是此代码本身不会导致InterruptedException,因此需要在线程上调用中断。 我用来尝试的代码是:

public class Test implements Runnable {

    public void run() {
        Object obj = new Object();
        Thread.currentThread().interrupt();
        try {
            synchronized(Thread.currentThread()) {
                obj.wait();
            }
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }

    public static void main(String[] args) {
        new Thread(new Test()).start();
    }
}

因此,A在理论上可能是正确的。 认证测试问题必须合理明确,规范在这一点上有点模棱两可,这使我认为这不是一个很好的测试问题。

C.“ TimeoutException”是伪造的。 如果等待超时超时,则该方法正常返回。

D.反转等待和通知呼叫的顺序无关紧要,它们都有相同的要求。

E.另一个线程所做的任何事情都不能使该线程在编写时正常完成。

F.方法等待在对象而不是线程上,不需要强制转换。

鉴于B绝对是正确的,并且它描述了Java程序员需要理解的重要点,而A基于对规范的模糊理解,如果您只能选择一个答案,我建议B。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM