Multi
Threading
Content
• Multi-Threading Fundamentals
• Thread States and Transitions
• Creating Threads - using Thread
class
• Creating Threads – using
Runnable interface
• Joining Threads
• Thread Priorities
• Synchronization
• Thread Communication
2
Multithreading Fundamentals
• Similar to Multiprocessing (OS can run several processes at the
same time)
• Only one process is actually executing at any given time. However, the
system appears to be running several programs simultaneously
• A thread is a sequential flow of
execution within a
program/process
• Single-threaded program can
handle one task at any time
• Multitasking allows single program
to run several concurrent threads
• Today’s modern OS supports
Multitasking inherently
3
Multithreading Fundamentals
• Multitasking
• Multitasking is a process of executing multiple tasks
simultaneously in order to maximize the resource (CPU) utilization
• A single task which requires a lot of processing can make the
entire application appear to be "sluggish" or unresponsive
• In a multitasked application, each task can be performed by a
separate process/thread
• Multitasking can be achieved in two ways:
• Process based multitasking (Multiprocessing)
• Thread based multitasking (Multithreading)
4
Multithreading Fundamentals
• Multithreading allows concurrent execution of two or more
parts of a program for attaining maximum utilization of CPU
• By using multithreading, your program can execute another
task during its idle time
• E.g.
• We have a program whose one part is sending a file over the network, another
part is reading the input from the keyboard while some other part is buffering the
next block of data to send
Thread 1
Multiple threads
Thread 2
Thread 3
sharing a single
Process
5
Multithreading Fundamentals
• Threads Support in Java
• Few programming languages directly support multithreading
• E.g., Java, Go, Scala, Rust etc.
• A thread in Java means two different things
• An instance of class java.lang.Thread
• A thread under execution
• An instance of class Thread is just an object
(like other objects in Java) that lives and dies on the heap
• A thread under execution is a process
(a lightweight sub-process) that executes in its own call stack
• In Java, there is one call stack per thread
6
Multithreading Fundamentals
• When we run any program in Java, the execution begins
from the main method
• Internally, the JVM creates a thread (called main thread)
that starts executing the code present inside the main
method
• There are other threads too.. Including the Garbage Collection
thread
Main • Although the main thread is
Thread created automatically (by
start start JVM), you can still control it
start
by obtaining a reference to
Thread Thread
this thread using
A Thread C currentThread() method of
B
the Thread class
Threads may switch or exchange data/results
7
Multithreading Fundamentals
• All the other threads will be created from the main thread
• Main thread must be the last thread to finish execution
(JVM will take care of this)
• E.g. Returns a reference to
the currently executing
class MainThread
thread object
{
public static void main(String[] args)
{
Thread t=Thread.currentThread();
t.setName("MainThread");
System.out.println("Name of thread is "+t);
}
}
Output:
Name of thread is:
Thread[MainThread,5,main]
8
• Thread States
• A thread can only be in one of the five states:
• New
• Runnable
• Running
• Non Runnable (Waiting/Blocked/Sleeping)
• Dead or Terminated
• A thread’s state changes based on:
Thread • Control methods such as: start, sleep, wait,
States & notify etc.
Transitions
9
Thread States & Transitions
10
• Thread States
• New
• Thread will be in a New state after the Thread
instance has been created
• It is a live thread object, but not yet a thread of
execution
• A new thread begins its life cycle in the new state
Thread • It remains in this state until the program starts the
thread
States & • It is also referred to as born thread
Transitions
11
Thread States & Transitions
• Thread States
• Runnable
• This is the state when a thread is considered eligible to run, but the scheduler has
not selected it to be the running thread
• A thread first enters the runnable state when the start() method is invoked
• A thread can also return to the runnable state after either running or coming back
from a blocked, waiting, or sleeping state
• When a thread is in the runnable state, it is considered as alive
12
Thread States & Transitions
• Thread States
• Running
• A thread is in the running state if the
thread scheduler has selected it
• The scheduler chooses a thread for
execution from the runnable pool
• A thread can transition out of a
running state for several reasons:
• Completed
• Waiting for I/O
• Blocked by another thread
13
Thread States &
Transitions
• Thread States
• Non Runnable (Waiting/blocked/sleeping)
• In this state, a thread is not eligible to run
(though the thread is still alive)
• A thread may be blocked waiting for a
resource (like I/O)
• A thread may be sleeping because the
thread’s run code (inside run()) tell it to
sleep for some period of time (using
sleep())
• A thread my be waiting because the
thread’s run code causes it to wait (using
wait())
14
Thread States & Transitions
• Thread States
• Dead or Terminated
• A thread is considered dead when its run() method completes execution
• Once a thread is dead, it can never be brought back for execution
• If you invoke a start() on a dead thread instance, you’ll get a runtime
exception
15
Creating Threads
• A thread can be created using any of the two ways
(i). By extending Thread class (Or)
(ii). By implementing Runnable interface and using Thread
class
• Thread class, along with Runnable interface is used to create and
run threads for utilizing Multithreading capabilities of Java
16
Creating Threads
• Thread Class
• Thread class provide constructors and methods to create and perform
operations on a thread
• Commonly used constructors of the Thread class
• Thread() Extending Thread class
• Thread(String str)
• Thread(Runnable r) Implementing Runnable Interface
• Thread(Runnable r, String str)
17
Creating Thread
• Thread class
• Thread class defines many methods for managing threads, few of these
methods are:
Method Name Description
setName() Give name to a thread
getName() Return thread’s name
getPriority() Return thread’s priority
isAlive() Checks if thread is still running or not
join() Wait for a thread to end
run()* Entry point for a thread
sleep() Suspend thread for a specified time
start() Starts a thread [with new call stack by calling
run() method]
18
Creating Threads
• Thread class
• When we extend the Thread class, we cannot override setName() &
getName() methods, as they’re declared as final in Thread class
• The sleep() method throws an interrupted exception, so it’s important to
handle the exception it throws
static void sleep(long milliseconds) throws InterruptedException
• run() method is used to perform some action for the thread. It can call
other methods, declare variables or use other classes just like the main
thread
19
• Thread class
• In order to create a thread using Thread class, you’ll
need to override the run() method
• This method provides an entry point for the thread & its
syntax is
public void run()
• Once the Thread object is created, you can start it by
Creating calling the start() method, which in turn invokes the
run() method, its syntax is
Threads void start()
20
Creating Threads
• Thread class – Example
class ThreadDemo extends Thread {
private Thread t;
private String threadName;
ThreadDemo( String name) {
threadName = name;
System.out.println("Creating " + threadName );
}
public void run() {
System.out.println("Running " + threadName );
try {
for(int i = 4; i > 0; i--) {
System.out.println("Thread: " + threadName + ", " + i);
// Let the thread sleep for a while.
Thread.sleep(5000);
}
} catch (InterruptedException e) {
System.out.println("Thread " + threadName + " interrupted.");
}
21
Creating Threads
• Example contd…
Output:
System.out.println("Thread " + threadName + " exiting."); Creating Thread-1
} Starting Thread-1
Creating Thread-2
} Starting Thread-2
Running Thread-1
// Driver Class Thread: Thread-1, 4
public class TestThread { Running Thread-2
Thread: Thread-2, 4
public static void main(String args[]) { Thread: Thread-1, 3
ThreadDemo T1 = new ThreadDemo( "Thread-1"); Thread: Thread-2, 3
T1.start(); Thread: Thread-1, 2
Thread: Thread-2, 2
ThreadDemo T2 = new ThreadDemo( "Thread-2"); Thread: Thread-1, 1
T2.start(); Thread: Thread-2, 1
}
Thread Thread-1 exiting.
Thread Thread-2 exiting.
}
22
Creating Threads
• Another Example
• Demonstrates basic threading techniques:
• Create a class derived from Thread
• Use sleep method
• What it does?
• Create four threads, which sleep for random amount of time
• After they finish sleeping, print their name
• Program has two classes:
• PrintThread -> Derived from Thread class
• ThreadTester -> Creates four PrintThread objects
23
Creating Threads
• Example contd…
class PrintThread extends Thread {
private int sleepTime;
// PrintThread constructor assigns name to thread
// by calling Thread constructor
public PrintThread( String name )
{
super( name ); // Calls the super class Thread constructor
// sleep between 0 and 5 seconds
sleepTime = (int) ( Math.random() * 5000 ); // Random integer value
System.err.println( "Name: " + getName() + "; sleep: " + sleepTime );
}
24
Creating Threads
• Example contd…
// execute the thread
public void run()
{
// put thread to sleep for a random interval
try {
System.err.println( getName() + " going to sleep" );
Thread.sleep( sleepTime );
}
catch ( InterruptedException exception ) {
System.err.println( exception.toString() );
}
// print thread name
System.err.println( getName() + " done sleeping" );
}
}
25
Creating Threads
• Example contd…
Output:
public class ThreadTester {
public static void main( String args[] ) Creating Thread-1
{ Starting Thread-1
PrintThread thread1, thread2, thread3, thread4; Creating Thread-2
Starting Thread-2
Running Thread-1
thread1 = new PrintThread( "thread1" ); Thread: Thread-1, 4
thread2 = new PrintThread( "thread2" ); Running Thread-2
thread3 = new PrintThread( "thread3" ); Thread: Thread-2, 4
thread4 = new PrintThread( "thread4" ); Thread: Thread-1, 3
Thread: Thread-2, 3
Thread: Thread-1, 2
System.err.println( "\nStarting threads" ); Thread: Thread-2, 2
Thread: Thread-1, 1
thread1.start(); Thread: Thread-2, 1
thread2.start(); Thread Thread-1 exiting..
Thread Thread-2 exiting..
thread3.start();
thread4.start();
System.err.println( "Threads started\n" );
}
}
26
Creating Threads
• Runnable Interface
• Another way to create a thread is by implementing the Runnable interface
• The Runnable interface has only one method i.e., run()
• First step is to implement the run() method that provides an action point
for the thread and contain the complete business logic inside it
• Second step is to instantiate a Thread class object using the given
constructor
Thread(Runnable threadObj, String threadName);
OR
Thread(Runnable threadObj)
27
Creating Threads
• Runnable Interface
• Launching a new thread:
3) Finally start the thread
1) Make a Runnable object (the thread’s job)
myThread.start();
Runnable threadJob = new MyRunnable();
2) Make a Thread object (the worker) and give it a Runnable (the job)
Thread myThread = new Thread(threadJob);
28
Creating Threads
• Runnable Interface – Example
// Let the thread sleep for a while.
class RunnableDemo implements Runnable {
Thread.sleep(50);
private Thread t; }
private String threadName; } catch (InterruptedException e) {
System.out.println("Thread " +
threadName + " interrupted.");
RunnableDemo( String name) { }
threadName = name; System.out.println("Thread " +
threadName + " exiting.");
System.out.println("Creating " +
threadName ); }
}
public void start () {
System.out.println("Starting " +
threadName );
public void run() {
if (t == null) {
System.out.println("Running " + threadName );
t = new Thread (this, threadName);
try { t.start ();
for(int i = 4; i > 0; i--) { }
System.out.println("Thread: " + }
threadName + ", " + i); }
29
Creating Threads
• Runnable Interface – Example
Contd…
Output:
Creating Thread-1
Starting Thread-1
public class TestThread {
Creating Thread-2
Starting Thread-2
public static void main(String args[]) { Running Thread-1
RunnableDemo R1 = new RunnableDemo( "Thread-1"); Thread: Thread-1, 4
Running Thread-2
R1.start();
Thread: Thread-2, 4
Thread: Thread-1, 3
RunnableDemo R2 = new RunnableDemo( "Thread-2"); Thread: Thread-2, 3
Thread: Thread-1, 2
R2.start();
Thread: Thread-2, 2
} Thread: Thread-1, 1
} Thread: Thread-2, 1
Thread Thread-1 exiting.
Thread Thread-2 exiting.
30
Creating Threads
• Another Example – Runnable Interface
class MyRunnableThread implements Runnable{
public static int myCount = 0;
public MyRunnableThread(){
// initialization code goes here
}
public void run() {
while(MyRunnableThread.myCount <= 10){
try{
System.out.println("Expl Thread: "+(++MyRunnableThread.myCount));
Thread.sleep(1000);
} catch (InterruptedException iex) {
System.out.println("Exception in thread: "+iex.getMessage());
}
}
}
}
31
Creating Threads
• Example contd…
public class RunMyThread {
public static void main(String a[]){
System.out.println("Starting Main Thread...");
MyRunnableThread mrt = new MyRunnableThread();
Thread t = new Thread(mrt);
t.start();
while(MyRunnableThread.myCount <= 10){
try{
System.out.println("Main Thread: "+(++MyRunnableThread.myCount));
Thread.sleep(1000);
} catch (InterruptedException iex){
System.out.println("Exception in main thread: "+iex.getMessage());
}
}
System.out.println("End of Main Thread...");
}
}
32
Creating Threads
• Special Cases
• Calling the run() method directly without using start() method
• Consider the given example on directly calling the run() method
• E.g.
public static void main( String args[] )
{
MyThread mt = new MyThread();
mt.run();
}
• In this case, the thread won’t create a new call stack, instead will start running in
the current call stack (i.e., call stack of main thread)
• Hence, there is no multithreading in this case
33
Creating Threads
• Special Cases
• Starting a thread twice
• A thread cannot be started twice (calling the start() method twice on the same
thread)
• When the second thread is called second time (using start()), it will throw an
IllegalThreadStateException
• E.g.
public static void main( String args[] )
{
MyThread mt = new MyThread();
mt.start();
mt.start(); //Exception thrown
}
34
What to
Choose?
Basis of Thread Runnable
Comparis
on
Basic Each thread creates a Multiple threads share the
unique object and gets same objects
associated with it
Memory & As each thread create a As multiple threads share
unique object, more the same object less
Performance memory required. memory is used. Less
Performance overhead overhead better
performance
Inheritance In Java, multiple If a class define thread
inheritance not allowed implementing the
hence, after a class extends Runnable interface it has
Thread class, it can not a chance of extending one
extend any other class class
Usage A user must extend thread If you only want to
class only if it wants to specialize run method
override the other methods then implementing
in Thread class Runnable is a better
option
Coupling Extending Thread class Implementing Runnable
introduces tight coupling as interface introduces loose
the class contains code of coupling as the code of
Thread class and also the Thread is separate form
job assigned to the thread the job of Threads
35
Joining Threads
• Sometimes, one thread needs to
know when other thread is
terminating
• Java supports two methods that are
used to check whether a thread has
finished its execution or not
(i). isAlive()
(ii). join()
• The isAlive() method returns true if
the thread upon which it is called is
still running else it returns false
• The join() method waits until the
thread on which it is called terminates
36
Joining Threads
• Example – isAlive()
public class MyThread extends Thread
{
public void run()
{
System.out.println("r1 "); Output
try {
Thread.sleep(500);
} true
catch(InterruptedException ie) true
{ }
System.out.println("r2 "); r1
}
r2
public static void main(String[] args)
{ r2
MyThread t1=new MyThread();
MyThread t2=new MyThread();
t1.start();
t2.start();
System.out.println(t1.isAlive());
System.out.println(t2.isAlive());
}
}
37
Joining Threads
• Example – without using join()
public class MyThread extends Thread public static void main(String[] args)
{ {
MyThread t1=new MyThread();
public void run()
MyThread t2=new MyThread();
{ t1.start();
System.out.println("r1 "); t2.start();
}
try {
}
Thread.sleep(500);
} Output:
r1
catch(InterruptedException ie){
r1
}
r2
System.out.println("r2 "); r2
}
38
• In the previous example, we created two threads t1 & t2
• Thread t1 starts its execution first by printing “r1” on the console
and goes to sleep for 500 ms (half second)
• Similarly, thread t2 starts and prints “r1” on the console & goes to
sleep for 500 ms
• After that thread t1 wakes up from sleep and prints “r2” similarly,
thread t2 wakes up and prints “r2”
Joining
Threads
• What if, we want thread t1 to finish its execution before t2 starts
39
Joining Threads
• Example – using join()
public class MyThread extends Thread t1.start();
try{
{
public void run()
t1.join();
{ //Waiting for t1 to
finish
System.out.println("r1 ");
}catch(InterruptedException ie){}
try { t2.start();
Thread.sleep(500); }
}catch(InterruptedException ie){ } }
System.out.println("r2 ");
Output
}
r1
public static void main(String[] args)
r2
{
• Join method on thread t1 ensures that it
r1
finishes its execution before thread t2
r2
MyThread t1=new MyThread(); starts
MyThread t2=new MyThread();
40
Thread Priorities
• Threads always run with some priority, usually represented as a number
between 1 and 10
• A thread’s priority determines how much CPU time a thread receives
• Higher the thread priority larger chance being executed first
• In most cases, a thread scheduler schedules the threads according to their
priority (known as preemptive scheduling)
• If a thread enters the Runnable state, and it has a higher priority than of the
threads in the thread-pool then the lower priority thread will be taken back to
Runnable state and the higher priority thread will be chosen to run
• In most cases, the running thread will of equal or greater priority than the
highest priority threads in the pool
41
Thread Priorities
42
Thread Priorities
43
Thread Priorities
44
Thread Priorities
45
Create Custom Thread with user-defined
name and Priority
46
Create Custom Thread with user-defined
name and Priority
47
Create Custom Thread with user-defined
name and Priority
48
Output
49
• Constants defined in Thread class
• There are 3 constants that defines the priority of a thread, these are
• public static int MIN_PRIORITY
• public static int NORM_PRIORITY
• public static int MAX_PRIORITY
• Default priority of a thread is 5 (NORM_PRIORITY)
• Value of MIN_PRIORITY is 1 & the value of MAX_PRIORITY is 10
Thread
Priorities
50
Thread Priorities
• Demo Example – Checking the CPU usage
• The example demonstration
creates two threads with
different priorities
• The run() method contains a
loop that counts the number
of iterations and stops when
the count reaches 10,000,000
or the static variable stop is
true
• Each time through the loop
the string in currentName will
be checked for the name of
executing thread
• This allows you to check how
often each thread has access
to the CPU
51
Thread Priorities
• Demo Example
class Priority implements Runnable {
int count;
Thread thrd;
static boolean stop = false; if(currentName.compareTo(thrd.getName()) != 0) {
static String currentName; currentName = thrd.getName();
System.out.println("In " +
Priority(String name) { currentName);
thrd = new Thread(this, name); }
count = 0; } while(stop == false && count < 10000000);
currentName = name; stop = true;
} System.out.println("\n" + thrd.getName() + The first
// Begin execution of new thread. " terminating."); thread to
complete
}
public void run() { 10,000,000
} iterations
System.out.println(thrd.getName() + " starting.");
will stop all
do { threads
count++;
52
Thread Priorities
• Demo Example
class PriorityDemo { System.out.println("Low priority thread counted
public static void main(String args[]) { to " +
Priority mt1 = new Priority("High Priority"); mt2.count);
Priority mt2 = new Priority("Low Priority");
}
// set the priorities
}
mt1.thrd.setPriority(Thread.NORM_PRIORITY+2);
mt2.thrd.setPriority(Thread.NORM_PRIORITY-2); Sample run:
// start the threads High Priority starting.
mt1.thrd.start();
In High Priority
mt2.thrd.start(); Giving mt1 a
higher priority Low Priority starting.
try {
than mt2
mt1.thrd.join(); In Low Priority
mt2.thrd.join(); In High Priority
Higher
} High Priority terminating. priority
catch(InterruptedException exc) { thread got a
Low Priority terminating. vast majority
System.out.println("Main thread interrupted.");
of CPU
High priority thread counted to 10000000
}
System.out.println("\nHigh priority thread counted to Low priority thread counted to 8183
" +
mt1.count);
53
Threads
54
Thread
55
Thread Creation
56
Thread Creation
• Thread creation by extending the Thread class
We create a class that extends the java.lang.Thread
class.
• This class overrides the run() method available in the
Thread class.
• A thread begins its life inside run() method.
• We create an object of our new class and call start()
method to start the execution of a thread.
• Start() invokes the run() method on the Thread object.
57
Thread Creation
• Thread creation by implementing the Runnable
Interface
We create a new class which implements
java.lang.Runnable interface and override run()
method.
• Then we instantiate a Thread object and call start()
method on this object.
58
Thread Creation
• Thread Class vs Runnable Interface
1.If we extend the Thread class, our class cannot extend
any other class because Java doesn’t support multiple
inheritance. But, if we implement the Runnable
interface, our class can still extend other base classes.
2.We can achieve basic functionality of a thread by
extending Thread class because it provides some inbuilt
methods like yield(), interrupt() etc. that are not
available in Runnable interface.
3.Using runnable will give you an object that can be
shared amongst multiple threads.
59
Thread Creation
60
Difference between Sleep & Wait
61
Thread extends
62
Threads Runnable
63
Thread Multiple Threads
64
Exercise
• Write a Java program that implements a multi-thread
application that has three threads. First thread
generates a random integer for every 1 second; second
thread computes the square of the number and prints;
third thread will print the value of cube of the number
65
Exercise
66
Exercise
67
resume()
68
resume()
69
Difference between Sleep & Wait
70
Difference between Sleep & Wait
71
Demo Wait
72
Synchronised
73
Difference between Sleep & Wait
74
Difference between Sleep & Wait
75
Demo Join
76
Demo Without Join
77
Demo isAlive
78
Thread Priority
79
Setting Custom Thread Name
80
Setting Custom Thread Name
81
Daemon Thread
82
Daemon Thread
83
Daemon Thread
84
Daemon Thread
85
Daemon Thread
86
Thank You
87