See the Tutorial List

threading Module In Python


As we have seen in the previous tutorial, threading module is used for creating, controlling and managing threads in python. In this tutorial, we will discuss about various functions and object types defined by the threading module.


threading Module Functions

This module provides the following functions for managing threads:

Here is the code snippet from last tutorial, we will be using this to see the various functions provided by the threading module in action.


threading.active_count() Function

This function returns the number of Thread objects currently alive.

import time
import threading

def thread1(i):
    time.sleep(3)
    #print('No. printed by Thread 1: %d' %i)

def thread2(i):
    time.sleep(3)
    #print('No. printed by Thread 2: %d' %i)

if __name__ == '__main__':
    t1 = threading.Thread(target=thread1, args=(10,))
    t2 = threading.Thread(target=thread2, args=(12,))
    t1.start()
    t2.start()
    print("No. of active threads: " + threading.active_count())
    t1.join()
    t2.join()

No. of active threads: 3

Try running the this code in the terminal above. You will see the number of thread count to be 3, because we have created 2 threads and there in the main thread in which the complete execution is taking place.


threading.current_thread()

This function will return the current Thread object, corresponding to the caller's thread of control(which is in the control of caller currently). If the caller's thread of control was not created through the threading module(for example the main thread), then a dummy thread object with limited functionality is returned.

import time
import threading

def thread1(i):
    time.sleep(3)
    #print('No. printed by Thread 1: %d' %i)

def thread2(i):
    time.sleep(3)
    #print('No. printed by Thread 2: %d' %i)

if __name__ == '__main__':
    t1 = threading.Thread(target=thread1, args=(10,))
    t2 = threading.Thread(target=thread2, args=(12,))
    t1.start()
    t2.start()
    print("Current thread is: " + threading.current_thread())
    t1.join()
    t2.join()

Current thread is: <_MainThread(MainThread, started 16152)>


threading.get_ident()

This function returns the thread identifier of the current thread. This is a nonzero integer value. If we started the thread, then this method will return its identifier, otherwise, it will return None.

We can use this method to index a dictionary of thread-specific data. Thread identifiers may be recycled when a thread exits(stops) and another thread is created.

threading.get_ident()

140578859194112


threading.enumerate()

This method returns a list of all Thread objects currently alive. The list includes daemonic threads(when the program quits, all the daemon threads associated with it are killed automatically), dummy thread objects created by the current thread, and the main thread.

Terminated threads and threads that have not yet been started are not present in this list.

 threading.enumerate()

[<_MainThread(MainThread, started 139890175817472)>, <Thread(Thread-1, started 139890151225088)>, <Thread(Thread-2, started 139890142832384)>]


threading.main_thread()

This method returns the main Thread object. In normal conditions, the main thread is the thread from which the python interpreter was started.

 threading.main_thread()

<_MainThread(MainThread, started 139890175817472)>


threading.settrace(fun)

This method is used to set a trace function/hook for all the threads started using the threadingmodule. The trace funtion is passed to sys.settrace() method for each thread, which is attache to the thread before the run() method is called.

The callback function which we want to act as the trace function will receive three arguments, frame (the stack frame from the code being run), event (a string naming the type of notification), and arg (an event-specific value)

def hello(frame, event, arg):
    print("Hello, I am a trace hook.")
threading.settrace(hello)

Try updating the code in the terminal at the top. Put the hello function outside the main method and the statement threading.settrace(hello) just above the statement where we call the start method for the threads.


threading.setprofile(fun)

This method is used to set a profile function for all threads started from the threading module. Just like the trace funtion, profile function is also passed to sys.setprofile() method for each thread, which is attache to the thread before the run() method is called.


threading.setprofile(hello)

threading.stack_size([size])

This method returns the thread stack size utilised when creating new threads. The size argument is optional and can be used to set the stack size to be used for creating subsequent threads, and must be 0 or a positive integer (D=default value is 0).

If changing the thread stack size is unsupported, a RuntimeError is raised.

If the specified stack size is invalid, a ValueError is raised.

Currently 32 KiB is the minimum stack size which is supported to provide enough stack space for the interpreter.


threading.TIMEOUT_MAX

Apart from the above specified functions, the threading module also defines a constant. If you specify a timeout value which is greater than the value of the TIMEOUT_MAX constant, you will get an OverflowError.


threading Module Objects

Apart from the functions specified above, the threading module also provides many classes whose objects are very useful in creating and managing threads.

Following are some of the Object types:

Object Description
Thread Object that represents a single thread of execution.
Lock Primitive lock object.
RLock RLock or Re-entrant lock object provides ability for a single thread to (re)acquire an already-held lock (recursive locking).
Condition Condition variable object causes one thread to wait until certain "condition" has been satisfied by another thread (such as change in state or some data value)
Event Its a more general version of condition variables, whereby a number of threads can be made to wait for some event to occur and all the threads waiting will only awaken when the event happens.
Semaphore Provides a "counter" of finite resources shared between threads block when none are available.
BoundedSemaphore Similar to a Semaphore but ensures that it never exceeds its initial value.
Timer Similar to Thread, except that it waits for a specified period of time before running.
Barrier Creates a "barrier" at which a specified number of threads must all arrive before they're all allowed to continue.

The above table gives a brief introduction of various object types in python threading module. We will discuss about all these objects in details in the next few tutorials.