简体   繁体   English

Java中的thread.join()问题

[英]thread.join() problem in java

My Code 我的密码

public class Main {

    public static void main(String[] args)throws Exception {
        Thread thread1=new Thread(new Runnable()
        {
            public void run()
            {
                System.out.println("Thread1");
            }
        });
        thread1.join();
        thread1.start();
        for (int i = 0; i < 1000; i++) {
            System.out.println(i);
        }
    }

}

Sometimes "Thread1" gets printed even before all the numbers get printed. 有时甚至在打印所有数字之前就打印“ Thread1”。 Any reason for that? 有什么理由吗? Shouldn't Thread1 should wait until main thread gets completed? Thread1是否应该等待主线程完成?

    thread1.join();
    thread1.start()

make it 做了

    thread1.start()
    thread1.join();

It will start a thread from main thread by thread1.start() and main thread will continue to execute at the very next line it will see thread1.join(); 它将通过thread1.start()从主线程开始一个线程,并且主线程将在下一行继续执行,它将看到thread1.join(); which will pause main thread's execution until thread1 finishes. 这将暂停主线程的执行,直到thread1完成。 so your work will get done 这样您的工作就可以完成

By calling Thread.join() The current thread waits for the thread you are calling join() . 通过调用Thread.join() ,当前线程等待您正在调用join()的线程。

In you case you are waiting for thread1 to complete before it even started. 在这种情况下,您正在等待thread1完成甚至尚未启动。

If you want thread1 to wait for the numbers to complete printing, you can use a CountDownLatch docs : 如果希望thread1等待数字完成打印,则可以使用CountDownLatch docs

public class Main {
    public static final CountDownLatch startSignal = new CountDownLatch(1);
    public static void main(String[] args)throws Exception {
        Thread thread1=new Thread(new Runnable()
        {
            public void run()
            {
                try {
                    startSignal.await();
                    System.out.println("Thread1");
                } catch (InterruptedException ex) {}
            }
        });
        thread1.start();
        for (int i = 0; i < 1000; i++) {
            System.out.println(i);
        }
        startSignal.countDown();
        thread1.join();
    }
}

Despite the fact that you should call thread1.start() before thread1.join() you actually don't know when the thread will be executed. 尽管您应该在thread1.start()之前调用thread1.start()thread1.join()您实际上并不知道何时执行线程。 It can happen while printing your i , it could happen before or it could happen after. 它可以在打印i时发生,它可以在发生之前或之后发生。 Depends on the thread scheduling mechanism of your OS. 取决于操作系统的线程调度机制。 Your correct code should look like this: 您的正确代码应如下所示:

public class Main {

public static void main(String[] args)throws Exception {
    Thread thread1=new Thread(new Runnable()
    {
        public void run()
        {
            System.out.println("Thread1");
        }
    });
    // start the thread
    thread1.start();
    // print the numbers... meanwhile your thread *could* get executed
    for (int i = 0; i < 1000; i++) {
        System.out.println(i);
    }
    // wait for thread1 to finish
    thread1.join();
}

} }

Actually, we should make sure the system has started the thread in accordance with our ".start()" request (which doesn't necessarily happen before start() returns), before invoking join(), as join() does not really wait until a thread dies, rather, it simply returns as soon as a thread isn't running. 实际上,我们应该确保在调用join()之前,系统已经根据我们的“ .start()”请求(不一定在start()返回之前发生)启动了线程,因为join()并不是真正的等到线程死亡,它只会在线程未运行时立即返回。 This can happen before the thread starts, or after it finishes. 这可能在线程启动之前或完成之后发生。 See "Taming Java Threads" by Allen Holub, page 87. Here is what I feel is the correct way to write this code: 请参阅第87页的Allen Holub的“ Taming Java Threads”。这是我认为编写此代码的正确方法:


import java.util.concurrent.Semaphore;

public class Main {

public static void main(String[] args)throws Exception { final Semaphore waitForThreadToStart = new Semaphore (0); Thread thread1=new Thread(new Runnable() { public void run() { waitForThreadToStart.release(); System.out.println("Thread1"); } }); thread1.start(); waitForThreadToStart.acquire(); // Wait for thread to start thread1.join(); // Now do the join. for (int i = 0; i < 10; i++) { System.out.println(i); } }

} }

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

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