Thread Join and Yield


Let us discuss Join() and yield() methods in Thread.


Join() method helps us to join one thread to the end of another thread.


In other words,
It causes the currently running thread to stop executing until the thread it joins with completes its execution.

Join() method simply takes the currently running thread and joins it to the end of thread on which we call join() method.

These 3 different overloaded methods available in Java for “join”

1) public void join()throws InterruptedException
Waits indefinitely for this thread to die.

2) public void join(long milliseconds)throws InterruptedException
Waits at most millis milliseconds for this thread to die.

3) public void join(long millis, int nanos)
Waits at most millis milliseconds plus nanos nanoseconds for this thread to die.

Example:

  1. Thread t = new Thread();
  2. t.start();
  3. t.join();
Thread t = new Thread();
t.start();
t.join();


Above code takes the currently running thread and joins it to the end of thread “t”.

So, thread “t” must finish its execution completely before any other thread resumes its execution.

This guarantees that thread “t” will always finish its execution without giving chance to any other thread.

Which Scenario we can consider join() method ?


Assume we have 2 threads named “t1” and “t2”

“t2” can’t do its work until “t1” finishes its work.

Means there is a dependency between the threads.

“t2” is dependent on “t1”.

In this case, we need to consider using join() on “t1” so that it always finishes its execution before any threads execute.

We can use join for the above case as below

  1. Thread t1 = new Thread();
  2. Thread t2 = new Thread();
  3. t1.start();
  4. t1.join();
  5. t2.start();
Thread t1 = new Thread();
Thread t2 = new Thread();
t1.start();
t1.join();
t2.start();

This will ensure that thread “t1” completes its execution before any other thread like “t2” in above case starts executing.

Example for Join()

  1. class ThreadJoin extends Thread{
  2.  public void run(){
  3.   for(int i=1;i<=5;i++){
  4.    try{
  5.     Thread.sleep(500);
  6.    }
  7. catch(Exception e){
  8. System.out.println(e);
  9. }
  10.   System.out.println(Thread.currentThread().getName() +"->"+i);
  11.   }
  12.  }
  13. }
  14. Public class ThreadJoinTest{
  15. public static void main(String args[]){
  16.  TestJoinMethod1 t1=new TestJoinMethod1();
  17. t1.setName("t1");
  18.  TestJoinMethod1 t2=new TestJoinMethod1();
  19. t2.setName("t2");
  20.  
  21.  t1.start();
  22.  try
  23. {
  24.  t1.join();
  25.  }
  26. catch(Exception e){
  27. System.out.println(e);
  28. }
  29.  
  30.  t2.start();
  31. System.out.println("abc");
  32.  
  33.  }
  34. }
class ThreadJoin extends Thread{
 public void run(){
  for(int i=1;i<=5;i++){
   try{
    Thread.sleep(500);
   }
catch(Exception e){
System.out.println(e);
}
  System.out.println(Thread.currentThread().getName() +"->"+i);
  }
 }
}
Public class ThreadJoinTest{
public static void main(String args[]){
 TestJoinMethod1 t1=new TestJoinMethod1();
t1.setName("t1");
 TestJoinMethod1 t2=new TestJoinMethod1();
t2.setName("t2");

 t1.start();
 try
{
 t1.join();
 }
catch(Exception e){
System.out.println(e);
}

 t2.start();
System.out.println("abc");

 }
}




We can observe that,thread “t1” completes the execution before any other thread began the execution, This is happening because, we have used “t1.join()”.

So “t1” executes and completes its execution first

Then main thread executes and then thread “t2” executes.

Order of “t2” and “main” is not guaranteed here.

Now just comment t1.join() in the above program and run it



We can observe here that, all threads executes based on Thread scheduler information and no thread waits for any other thread to complete the execution

Hence we can see the output with mixed output from all the threads.


Yield() method

This method gives hint to the scheduler that the thread is willing to yield its current use of a processor to use it for some other threads.

In other words,
Yielding thread informs the scheduler that “ I am not doing critical work, if you want you can schedule other thread in my place ”.

This is just a hint given by yielding thread and not guaranteed to have any effect at all.

In fact, Thread scheduler can ignore its request.

Only one method is available in java for yield, which is as below

  1. public static void yield()
public static void yield()

yield() keeps the currently executing thread into “ Runnable ” state not into “Wait” or “Blocked” state.

Remember “ yield() ” is just a request , so there is no guarantee that its request is always considered by Thread scheduler.

Example for yield()

  1. class ThreadYield extends Thread
  2. {
  3. public void run(){
  4.  
  5. System.out.println(Thread.currentThread().getName() + " started");
  6.  //for (int i = 1; i < 10; i++) {
  7.    
  8.       System.out.println(Thread.currentThread().getName() + " yielding");  
  9.       Thread.yield();//It Causes the currently executing thread to temporarily pause and allow other threads to execute.
  10.      
  11. // }
  12.   System.out.println(Thread.currentThread().getName()+"--> Finsihed execution");
  13.  
  14. }
  15. }
  16.  
  17. public class YieldTest{
  18. public static void main(String args[]){
  19.  ThreadYield t1=new ThreadYield();
  20. t1.setName("Thread1");
  21.  ThreadYield t2=new ThreadYield();
  22. t2.setName("Thread2");
  23.  
  24. ThreadYield t3=new ThreadYield();
  25. t3.setName("Thread3");
  26.  
  27. t1.start();
  28. t2.start();
  29. t3.start();
  30. }
  31. }
class ThreadYield extends Thread
{
public void run(){

System.out.println(Thread.currentThread().getName() + " started");
 //for (int i = 1; i < 10; i++) {
    
      System.out.println(Thread.currentThread().getName() + " yielding");  
      Thread.yield();//It Causes the currently executing thread to temporarily pause and allow other threads to execute.
      
// }
  System.out.println(Thread.currentThread().getName()+"--> Finsihed execution");

}
}

public class YieldTest{
public static void main(String args[]){
 ThreadYield t1=new ThreadYield();
t1.setName("Thread1");
 ThreadYield t2=new ThreadYield();
t2.setName("Thread2");

ThreadYield t3=new ThreadYield();
t3.setName("Thread3");

t1.start();
t2.start();
t3.start();
}
}




Please note that, you may get different output based on your Operating system and scheduling algorithm used there.

The program is written in such a way that, we have started 3 threads and called yield method, so any thread which gets a chance to execute will first print “started” message to the console and then calls “yield” method which is just a request to thread scheduler to give chance to other threads for execution.

If you observe the first output, Thread1 prints “started” message on console as it gets first chance to execute

Then calls “yield” method which requests thread scheduler to stop its execution and thread scheduler consider this request gracefully and Thread3 prints “started” and it continues thereafter.

Note:Yield() method only requests , so there is no guarantee that the request is considered always by thread scheduler.

About the Author

Karibasappa G C (KB)
Founder of javainsimpleway.com
I love Java and open source technologies and very much passionate about software development.
I like to share my knowledge with others especially on technology 🙂
I have given all the examples as simple as possible to understand for the beginners.
All the code posted on my blog is developed,compiled and tested in my development environment.
If you find any mistakes or bugs, Please drop an email to kb.knowledge.sharing@gmail.com

Connect with me on Facebook for more updates

Share this article on