from threading import Thread, Lock, Barrier, current_thread from multiprocessing import Process, Pipe, current_process from queue import Queue from time import sleep import os clear = lambda: os.system('cls') # Simple threading example def thread_hello(): other = Thread(target=thread_say_hello, args=()) other.start() thread_say_hello() def thread_say_hello(): print('hello from', current_thread().name) # thread_hello() # Simple multiprocessing example def process_hello(): other = Process(target=process_say_hello, args=()) other.start() process_say_hello() def process_say_hello(): print('hello from', current_process().name) # process_hello() # A race condition counter = [0] def increment(): count = counter[0] sleep(0) # try to force a switch to the other thread counter[0] = count + 1 def race(): other = Thread(target=increment, args=()) other.start() increment() other.join() # wait for other thread to complete print('count is now:', counter[0]) # race() # Using a synchronized data structure queue = Queue() def increment2(): count = queue.get() sleep(0) # try to force a switch to the other thread queue.put(count + 1) def queue_increment(): other = Thread(target=increment2, args=()) other.start() queue.put(0) increment2() other.join() print('count is now:', queue.get()) # queue_increment() class Fib(object): a = 0 b = 1 def compute(self, n): a, b = self.a, self.b while n > 0: a, b = b, a + b n -= 1 return a class Fact(object): a = 1 def compute(self, n): if n <= self.a: return self.a return n * self.compute(n - 1) fibber1 = Fib() fibber2 = Fib() facter1 = Fact() facter2 = Fact()