超时并行执行的线程

时间:2016-02-16 15:23:59

标签: java wait synchronize

在处理并行线程时,输出应该是:"等待,完成"!目前它是:"等待,不应该显示,完成"。有人可以帮忙吗? 我的主要:

int k=tokens.length(); //does not work

班级主管:

public class Test {
    public static void main(String[] args) {
        Supervisor a = new Supervisor();
        System.out.println("done");
    }
}

和Calculator类:

public class Supervisor {       
     public Supervisor()  { 
            Calculate t1 = new Calculate();
            t1.start(); 
            synchronized(t1){  
                System.out.println("wait");
                try {
                    t1.wait(1000);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }           
        }   
    }
}

2 个答案:

答案 0 :(得分:0)

此代码:

        t1.start(); 
        synchronized(t1){  

可以导致t1run部分之前到达synchronized。解决这个问题:

        synchronized(t1){  
          t1.start(); 

还有关于sleep的文档:

  

导致当前正在执行的线程进入休眠状态(暂时停止执行)......

使用此代码,事情看起来更清晰:

public class Calculate extends Thread {

    public Calculate() {
    }

    @Override
    public void run() {
        synchronized (this) {
            try {
                System.out.println("Calc sleeping");
                Thread.sleep(10000);
                System.out.println("not supposed to be shown");
            } catch (InterruptedException ex) {
                Thread.currentThread().interrupt();
            }
            notify();
        }
    }
}

public class Supervisor {

    public Supervisor() {
        Calculate t1 = new Calculate();
        System.out.println("Super " + Thread.currentThread().getName());
        synchronized (t1) {
            t1.start();
            System.out.println("wait");
            try {
                System.out.println("Super waiting");
                t1.wait(1000);
                System.out.println("Super awake");
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
            System.out.println("finish");
        }
    }
}

打印:

Super main
wait
Super waiting
Calc sleeping
not supposed to be shown
Super awake
finish

Supervisor睡觉时,Calculate醒来并运行至完成时间为10秒,然后调用notify唤醒Supervisor以继续。

答案 1 :(得分:0)

您的代码的问题在于主管必须在wait之前获取锁定,但计算器只是在睡眠和println之后释放锁定。您可以通过向println("not supposed")添加断点并获取JVM的线程转储来轻松地查看它:运行管理程序的main线程在构造函数中被阻塞,等待monitorentry(JVM)行话)。

t1.start(); 
synchronized(t1) {

表示如果计算器执行锁定,则只有在释放锁定(睡眠后)时才会执行主管中synchronized块内的代码。您的代码存在许多问题,并且它不是惯用的,也不正确,所以我给您以下参考

监:

Calculate calculator = new Calculate();
Thread thread = new Thread(calculator);
thread.start();

synchronized (calculator) {
    while (!calculator.completed) {
        calculator.wait(1000);
        if (!calculator.completed) {
            System.out.println("Supervisor here: waited 1s, still not ready");
        }
    }
}

System.out.println("Computation ended and result consumed. Can rest :)");

任务

public class Calculate implements Runnable {

    public volatile boolean completed;

    @Override
    public void run() {
        try {
            System.out.println("Calculator: Started!");
            Thread.sleep(10000);
            System.out.println("Calculator: I'm done!");
        } catch (InterruptedException e) {
            throw new RuntimeException(e);
        }

        synchronized(this){
            completed = true;
            notify();
        }
    }
}