The lifecycle of a thread in Java
Thread is a topic that can not be circumnavigated in Java. Today, this article will explain the life cycle of threads in Java in detail, hoping to give you some inspiration.
Status of Thread in Java
Thread has six states in Java, which are:
- NEW – The newly created Thread has not yet been executed
- RUNNABLE – RUNNABLE threads, both ready to run and running.
- BLOCKED – A thread that is waiting for a resource lock
- WAITING – WAITING indefinitely for another thread to perform a particular operation
- TIMED_WAITING – Waiting for another thread to perform a particular operation for a certain amount of time
- TERMINATED – The thread is TERMINATED
We can use a graph to visualize it:
The following is the definition in the JDK code:
public enum State {
/** * Thread state for a thread which has not yet started. */
NEW,
/** * Thread state for a runnable thread. A thread in the runnable * state is executing in the Java virtual machine but it may * be waiting for other resources from the operating system * such as processor. */
RUNNABLE,
/**
* Thread state for a thread blocked waiting for a monitor lock.
* A thread in the blocked state is waiting for a monitor lock
* to enter a synchronized block/method or
* reenter a synchronized block/method after calling
* {@link Object#wait() Object.wait}.
*/
BLOCKED,
/**
* Thread state for a waiting thread.
* A thread is in the waiting state due to calling one of the
* following methods:
* <ul>
* <li>{@link Object#wait() Object.wait} with no timeout</li>
* <li>{@link #join() Thread.join} with no timeout</li>
* <li>{@link LockSupport#park() LockSupport.park}</li>
* </ul>
*
* <p>A thread in the waiting state is waiting for another thread to
* perform a particular action.
*
* For example, a thread that has called <tt>Object.wait()</tt>
* on an object is waiting for another thread to call
* <tt>Object.notify()</tt> or <tt>Object.notifyAll()</tt> on
* that object. A thread that has called <tt>Thread.join()</tt>
* is waiting for a specified thread to terminate.
*/
WAITING,
/**
* Thread state for a waiting thread with a specified waiting time.
* A thread is in the timed waiting state due to calling one of
* the following methods with a specified positive waiting time:
* <ul>
* <li>{@link #sleep Thread.sleep}</li>
* <li>{@link Object#wait(long) Object.wait} with timeout</li>
* <li>{@link #join(long) Thread.join} with timeout</li>
* <li>{@link LockSupport#parkNanos LockSupport.parkNanos}</li>
* <li>{@link LockSupport#parkUntil LockSupport.parkUntil}</li>
* </ul>
*/
TIMED_WAITING,
/** * Thread state for a terminated thread. * The thread has completed execution. */
TERMINATED;
}
Copy the code
NEW
NEW indicates that the thread has been created but has not yet started execution. Let’s look at an example of NEW:
public class NewThread implements Runnable{
public static void main(String[] args) {
Runnable runnable = new NewThread();
Thread t = new Thread(runnable);
log.info(t.getState().toString());
}
@Override
public void run(a) {}}Copy the code
The above code will print:
NEW
Copy the code
Runnable
Runnable indicates that the thread is in the executable state. Including running and ready to run.
Why are they both called Runnable? We know that in a multitasking environment, there are only a limited number of cpus, so tasks are executed in a round-robin manner. The THREAD scheduler in the JVM allocates a specific execution time to each thread, and when the execution time is up, the thread scheduler frees the CPU for other Runnable threads to execute.
Let’s look at an example of Runnable:
public class RunnableThread implements Runnable {
@Override
public void run(a) {}public static void main(String[] args) {
Runnable runnable = new RunnableThread();
Thread t = newThread(runnable); t.start(); log.info(t.getState().toString()); }}Copy the code
The above code will print:
RUNNABLE
Copy the code
BLOCKED
BLOCKED indicates that a thread is waiting for a resource lock that is currently being held by another thread.
Let’s take an example:
public class BlockThread implements Runnable {
@Override
public void run(a) {
loopResource();
}
public static synchronized void loopResource(a) {
while(true) {
// Infinite loop}}public static void main(String[] args) throws InterruptedException {
Thread t1 = new Thread(new BlockThread());
Thread t2 = new Thread(new BlockThread());
t1.start();
t2.start();
Thread.sleep(1000);
log.info(t1.getState().toString());
log.info(t2.getState().toString());
System.exit(0); }}Copy the code
In the above example, because T1 is an infinite loop, it will hold the resource lock all the time, causing T2 to be unable to obtain the resource lock and thus remain BLOCKED.
We get the following result:
12:40:11.710 [main] info.flydean.blockthread - RUNNABLE 12:40:11.713 [main] info.flydean.blockthread - RUNNABLE 12:40:11.713 [main] info.flydean.blockthread - RUNNABLE 12:40:11.713 [main] info.flydean.blockthread - BLOCKEDCopy the code
WAITING
WAITING indicates that a thread is WAITING for another thread to perform a specific operation. There are three ways to cause a thread to be in WAITTING state:
- object.wait()
- thread.join()
- LockSupport.park()
The 1,2 methods do not need to pass in time parameters.
Let’s look at an example of use:
public class WaitThread implements Runnable{
public static Thread t1;
@Override
public void run(a) {
Thread t2 = new Thread(()->{
try {
Thread.sleep(10000);
} catch (InterruptedException e) {
Thread.currentThread().interrupt();
log.error("Thread interrupted", e);
}
log.info("t1"+t1.getState().toString());
});
t2.start();
try {
t2.join();
} catch (InterruptedException e) {
Thread.currentThread().interrupt();
log.error("Thread interrupted", e);
}
log.info("t2"+t2.getState().toString());
}
public static void main(String[] args) {
t1 = new Thread(newWaitThread()); t1.start(); }}Copy the code
In this example, we call t2.join(), which makes the T1 thread calling it WAITTING.
Let’s look at the output:
12:44:12.958 [Thread-1] INFO com.flydean.WaitThread - t1 WAITING
12:44:12.964 [Thread-0] INFO com.flydean.WaitThread - t2 TERMINATED
Copy the code
TIMED_WAITING
The TIMED_WAITING state means that you are waiting for another thread to perform some specific operation for a finite amount of time.
There are five ways to achieve this state in Java:
- thread.sleep(long millis)
- Wait (int timeout) or wait(int timeout, int nanos)
- thread.join(long millis)
- LockSupport.parkNanos
- LockSupport.parkUntil
Let’s take an example:
public class TimedWaitThread implements Runnable{
@Override
public void run(a) {
try {
Thread.sleep(5000);
} catch (InterruptedException e) {
Thread.currentThread().interrupt();
log.error("Thread interrupted", e); }}public static void main(String[] args) throws InterruptedException {
TimedWaitThread obj1 = new TimedWaitThread();
Thread t1 = new Thread(obj1);
t1.start();
// The following sleep will give enough time for ThreadScheduler
// to start processing of thread t1
Thread.sleep(1000); log.info(t1.getState().toString()); }}Copy the code
In the above example we called thread.sleep (5000) to put the Thread in TIMED_WAITING state.
Look at the output:
12:58:02. [the main] INFO 706 com. Flydean. TimedWaitThread - TIMED_WAITINGCopy the code
So, what’s the difference between TIMED_WAITING and WAITTING?
TIMED_WAITING if no specific operation is performed by another thread within a given period of time, the TIMED_WAITING will wake up and enter the queue for the resource lock. If the lock can be obtained, the TIMED_WAITING state will become Runnable, and if the lock cannot be obtained, it will become BLOCKED.
TERMINATED
TERMINATED indicates that the thread is TERMINATED. Let’s look at an example:
public class TerminatedThread implements Runnable{
@Override
public void run(a) {}public static void main(String[] args) throws InterruptedException {
Thread t1 = new Thread(new TerminatedThread());
t1.start();
// The following sleep method will give enough time for
// thread t1 to complete
Thread.sleep(1000); log.info(t1.getState().toString()); }}Copy the code
Output result:
13:02:38. [the main] INFO 868 com. Flydean. TerminatedThread - TERMINATEDCopy the code
Examples of this article can be found at github.com/ddean2009/l…
See flydean’s blog for more tutorials