7. Multi-threading
Multithreading allows you to break down
an application into multiple sub-tasks
and run these tasks simultaneously.
If you use multithreading properly, your application speed
, performance
, and rendering can all be improved.
Multithreading is defined as the ability of a processor to execute multiple threads concurrently
.
7.1 Process
A process is an instance
of a computer program that is being executed
Its basically the program in execution
. When you start an application in your computer (like a browser or text editor), the operating system creates a process.
7.2 Thread
A thread is nothing but an independent flow of execution
. It can also be defined as an instance of a process
.
A process can be divided into multiple independend sub-tasks, each sub-tasks is called thread.
7.3 Multi Threading in Python
Python provides one inbuilt module "threading"
to provide support for developing threads. Hence developing multi threaded Programs is very easy in python.
Every Python Program by default contains one thread which is nothing but MainThread.
import threading
print("Current Executing Thread:",threading.current_thread().getName())
7.4 Ways of Creating Thread in Python
We can create a thread in Python by using 3 ways
- Creating a Thread without using any class
- Creating a Thread by extending Thread class
- Creating a Thread without extending Thread class
# Without multi threading:
def display():
for i in range(1,5):
print("Child Thread")
time.sleep(1)
display()
for i in range(1, 5):
print("Main Thread")
time.sleep(.7)
7.4.1 Creating a Thread without using any class
If multiple threads present in our program, then we cannot expect execution order
and hence we cannot expect exact output for the multi threaded programs.
import time
from threading import *
def display():
for i in range(1,5):
print("Child Thread")
time.sleep(1)
# creating Thread object
t=Thread(target=display)
# starting of Thread
t.start()
for i in range(1, 5):
print("Main Thread")
time.sleep(.7)
- Thread with arguments
import time
from threading import *
def test(id) :
for i in range(id):
print(current_thread().getName(), '-->', i)
time.sleep(0.5)
thred = [Thread(target=test , args = (i,)) for i in [5 , 2 , 3]]
print(thred)
for t in thred:
t.start()
print(thred)
7.4.2 Creating a Thread by extending Thread class
import time
from threading import *
class MyThread(Thread):
def run(self):
for i in range(5):
print("Child Thread-1")
time.sleep(1)
t=MyThread()
t.start()
for i in range(5):
print("Main Thread-1")
time.sleep(0.7)
7.4.3 Creating a Thread without extending Thread class
import time
from threading import *
class Test:
def display(self):
for i in range(5):
print("Child Thread-2")
time.sleep(1)
obj=Test()
t=Thread(target=obj.display)
t.start()
for i in range(5):
print("Main Thread-2")
time.sleep(.7)
7.5 Shared variables using Threading
shared_var = 0
lock_var = threading.Lock()
def test4(x) :
global shared_var
with lock_var :
shared_var = shared_var + 1
print("value of x %d and value of shareed_var %d " %(x, shared_var))
time.sleep(1)
thread5 = [threading.Thread(target=test4 , args = (i,)) for i in [1,2,3,4,4,5]]
for t in thread5 :
t.start()
7.6 Terms
start()
- When a thread instance is created, it doesn’t start executing until its start() method (which invokes the target function with the arguments you supplied) is invoked.
run()
- The .run() method executes any target function belonging to a given thread object that is now active.
- It normally executes in the background after the start() method is invoked.
import threading
class CustomThread(threading.Thread):
def run(self):
print("This is my custom run!")
custom_thread = CustomThread()
custom_thread.start()
current_thread()
- We use the current_thread() function to get the current thread object.
import threading
print("Current Executing Thread:",threading.current_thread().getName())
Thread Identification Number (ident)
from threading import *
def test():
print("Child Thread")
t=Thread(target=test)
t.start()
print("Main Thread Identification Number:", current_thread().ident)
print("Child Thread Identification Number:", t.ident)
active_count()
- This function returns the number of active threads currently running
import time
from threading import *
def test(id) :
for i in range(id):
time.sleep(0.5)
thred = [Thread(target=test , args = (i,)) for i in [10 , 2 , 5]]
for t in thred:
t.start()
print("The Number of active Threads:",active_count())
time.sleep(3)
print("The Number of active Threads:",active_count())
enumerate()
- This function returns a list of all active threads currently running
from threading import *
threads =enumerate()
for i in threads:
print(i)
isAlive()
- isAlive() method checks whether a thread is still executing or not.
join()
- If a thread wants to wait until completing some other thread then we should go for join() method.
Disadvantages of multithreading
- It needs more
careful synchronization
. - My have
Deadlocks
andRace conditions
- It imposes context
switching overhead
. - It can consume a large space of stocks of blocked threads.
- It needs support for thread or process.
- If a parent process has several threads for proper process functioning, the child processes should also be multithreaded because they may be required.
Advantages of multithreading
- Enables
efficient utilization
of the resources as the threads share the data space and memory. - Allows the
concurrent and parallel
exwcution of various tasks. - Reduction in
time consumption or response time
, thereby increasing the performance.
7.7 Multi Tasking
Executing several tasks simultaneously is the concept of multitasking.
There are 2 types of Multi Tasking
- Process based Multi Tasking
- Thread based Multi Tasking
7.8 Process based Multi Tasking:
Executing several tasks simmultaneously where each task is a seperate independent process
is called process based multi tasking.
Eg: while typing python program in the editor
we can listen mp3
audio songs from the same
system. At the same time we can download
a file from the internet. All these taks are executing
simultaneously and independent of each other. Hence it is process based multi tasking.
This type of multi tasking is best suitable at operating system level
.
7.9 Thread based MultiTasking
Executing several tasks simultaneously where each task is a seperate independent part of the same program
, is called Thread based multi tasking, and each independent part is called a Thread.
This type of multi tasking is best suitable at programmatic level
.
Whether it is process based or thread based, the main advantage of multi tasking is to improve performance of the system by reducing response time.