简体   繁体   中英

isAlive() returns false

I have a class MyTunnel which extends Thread class :

public class MyTunnel extends Thread {
    protected Object obj;
    public MyTunnel() {
        super(MyTunnel.class.getName());
        obj = new Object();
        prepare();
    }
    public void prepare() {
        System.out.println("Before starting...");
        start();
        synchronized(obj) {
            try {
                obj.wait(3000);
            } catch (InterruptedException e) {
                System.out.println("Error while waiting thread to start");
            }
        }

        System.out.println("After starting...");
    }

    @Override
    public void run() {
        System.out.println("running...");
    }

}

When I run following code on main thread:

System.out.println("Before creating tunnel...");
MyTunnel tunnel = new MyTunnel();
System.out.println("After creating tunnel...");

System.out.println("Is tunnel alive ? " + tunnel.isAlive());

I see print out like this:

Before creating tunnel...
Before starting...
running...
After starting...
After creating tunnel...
Is tunnel alive ? false

My question is, why tunnel.isAlive() returns false (in last print out message)?

But if I change prepare() function to:

public void prepare() {
    System.out.println("Before starting...");
    start();
    System.out.println("After starting...");
}

run the code again, tunnel.isAlive() then returns true. Why?

The first scenario:

Your current ("main") thread starts the new thread, then the call obj.wait(3000); causes the current thread to wait with a timeout of 3 seconds. It's not the new thread that waits!

As the current thread waits, the new thread is executed. It only writes "running..." and finishes very quickly.

Thus, the "main" thread is resumed (after 3 seconds), the new thread is already dead, so isAlive() returns false .

The second scenario:

Your current ("main") thread starts the new thread and continues executing.

The new thread may or may not run while the main thread does just a few System.out.println() calls.

Thus, there's a chance that the new thread is not yet executed and the new thread is still alive, so isAlive() returns true .

Note that it may happen that the new thread is executed just after having been started in the second scenario. So even in the second scenario isAlive() may return false , but the chances are lower than in the first one (-> race conditions).


PS if you include any "heavy" operation in the second scenario just before calling isAlive() , then it's likely that the result is false . Pls try the following:

    System.out.println("Before creating tunnel...");
    final MyTunnel tunnel = new MyTunnel();
    System.out.println("After creating tunnel...");

    for (int i = 0; i < 100; ++i) {
        System.out.print("");
    }

    System.out.println("Is tunnel alive ? " + tunnel.isAlive()); // returns false on my machine

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

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