Python - thread examples

From NoskeWiki
Jump to navigation Jump to search


NOTE: This page is a daughter page of: Python

Here are some examples of how to use threads in python3.

Simple Python thread example: thread > start > join

Two threads printing numbers... `start` them and `join` to wait for them all to finish.

import threading
import time

def print_even_numbers():
    for i in range(0, 10, 2):
        print(f"E:{i}", end='> ')

def print_odd_numbers():
    for i in range(1, 10, 2):
        print(f"Odd:{i}", end='> ')
        time.sleep(0.5)  # Significantly slower.

# Create threads:
even_thread = threading.Thread(target=print_even_numbers)
odd_thread = threading.Thread(target=print_odd_numbers)
# Start threads:
# Wait for both threads to complete:
# Will print out something like:
#  "E:0> Odd:1> E:2> E:4> Odd:3> E:6> E:8> Odd:5> Odd:7> Odd:9>"
# But not necessarily in that exact order
print("Both threads have finished!")

A python thread pool and lock example: ThreadPoolExecutor > submit > lock

This uses a thread pool where all threads increment a single global variable, and use a lock on it to avoid race conditions.

import threading
from concurrent.futures import ThreadPoolExecutor

# Define the shared counter and its lock:
counter = 0
counter_lock = threading.Lock()

increments_per_worker = 1000  # Increments each worker will perform.

def worker():
    global counter
    for _ in range(increments_per_worker):
        with counter_lock:  # Acquire the lock.
            counter += 1    # Safely increment the counter.
        # Release the lock when leaving the 'with' block.

num_workers = 5  # Number of workers in the thread pool.

# Using ThreadPoolExecutor to manage our workers.
with ThreadPoolExecutor(max_workers=num_workers) as executor:
    # Start all workers.
    futures = [executor.submit(worker) for _ in range(num_workers)]
    # Wait for all workers to finish.
    for future in futures:

print(f"Expected counter value: {increments_per_worker * num_workers}")
print(f"Actual counter value: {counter}")

# NOTE: Without the lock (try to take it away) race conditions might
# mean we don't get exactly 5000 as our counter value.

A python array of thread objects (a class inheriting "Thread")

import threading
import random
import time

class BoardGame:
    def __init__(self, board_size=10):
        self.board_size = board_size     # There are (by default) ten squares in the game.
        self.board = [' '] * board_size
        self.treasure_positions = random.sample(range(board_size), 3)
        print(f'Treasure positions {self.treasure_positions}\n')
        for pos in self.treasure_positions:  # Put a 'T' in the random positions.
            self.board[pos] = 'T'

class Player(threading.Thread):
    def __init__(self, name, game):
        super().__init__() = name = game
        self.position = 0
        self.treasures = 0

    def run(self):
        while self.position <
            if[self.position] == 'T':
                self.treasures += 1
                print(f'{} picked up a treasure at position {self.position}!')
                time.sleep(random.uniform(0.01, 0.2))  # Extra time penalty to pickup treasure.
      [self.position] = ' '

            time.sleep(random.uniform(0.5, 2))  # Randomize speed of progress.
            self.position += 1  # Player moves ahead one spot.

        print(f'{} reached the finish line with {self.treasures} treasures!')

board_game = BoardGame()

players = [Player("Alice", board_game),
           Player("Bob", board_game), 
           Player("Charlie", board_game)]

for player in players:

for player in players:

# Determine the winner
winner = max(players, key=lambda p: p.treasures)
print(f'{} wins with {winner.treasures} treasures!')

Output might be something like:

Treasure positions [6, 7, 1]

Charlie picked up a treasure at position 1!
Alice picked up a treasure at position 6!
Alice picked up a treasure at position 7!
Bob reached the finish line with 0 treasures!
Charlie reached the finish line with 1 treasures!
Alice reached the finish line with 2 treasures!
Alice wins with 2 treasures!