线程完成后运行线程的run()方法

时间:2011-12-10 13:27:08

标签: java multithreading concurrency

我试图在线程完成后了解Thread对象的状态。我在一本书中读到,一旦线程完成了run()方法,线程对象仍然是头上的有效对象,仍然可以用作实例对象,你仍然可以在其上调用方法。我决定尝试使用以下示例:

class DieThread implements Runnable{

    int y = 0;

    public void run(){
        for(int x=0; x<100; x++){
            System.out.println("             " + Thread.currentThread().getName());
            System.out.println("y is " + y);
            y++;
            System.out.println("y is " + y);
        }
    }   
}

class ZiggyTest2{
    public static void main(String[] args){     

        DieThread d = new DieThread();

        Thread a = new Thread(d);
        Thread b = new Thread(d);
        Thread c = new Thread(d);

        a.start();
        b.start();
        c.start();

        try{
            a.join();
            b.join();
            c.join();
        }catch(Exception e){
            System.out.println(e);
        }

        System.out.println("Running C's Run");
        c.run();        
    }
}

main()使用join()等待其他3个线程完成。然后调用c的run()方法,但由于某种原因,它不会从run()方法中打印出任何内容。以下是运行上述程序后输出的最后几行。

y is 287
y is 287
y is 288
y is 289
             Thread-1
             Thread-0
y is 289
y is 289
y is 290
y is 291
             Thread-1
             Thread-0
y is 291
y is 291
y is 292
y is 293
             Thread-1
             Thread-0
y is 293
y is 293
y is 294
y is 295
             Thread-0
y is 295
y is 296
             Thread-0
y is 296
y is 297
             Thread-0
y is 297
y is 298
             Thread-0
y is 298
y is 299
             Thread-0
y is 299
y is 300
Running C's Run

即使线程已经完成,由于c.run()调用,我期望y的值为400。

有什么想法吗?

由于

3 个答案:

答案 0 :(得分:3)

如果你扩展Thread类,它就可以了。现在它在Thread.exit()

之后检查Runnable目标null

答案 1 :(得分:1)

同步访问对象DieThread

的状态
synchronized(this) {
    System.out.println("             " + Thread.currentThread().getName());
    System.out.println("y is " + y);
    y++;
    System.out.println("y is " + y);
}

答案 2 :(得分:1)

您所观察到的内容的原因隐藏在Thread类的实现中。

当您调用c.run()时,您正在线程对象上调用run方法。这被指定为调用run对象的target方法(即Thread构造函数中提供的runnable),如果它不是null。如果targetnull,则Thread.run()方法不执行任何操作。

好的,所以你提供了一个非空的target

事实上,当Thread完成时,调用Thread.exit()方法进行清理。清理所做的一件事就是将null分配给target。 (代码中有关于需要积极清除引用的注释以及错误ID。不幸的是,缺少相应的错误报告,因此无法知道他们执行此操作的真实原因。)

无论如何,最重要的是,您无法通过调用run()重新运行目标对象的Thread.run()方法。但是你可以直接调用目标对象的run()方法......如果你有目标引用。