共享变量
当多个线程同时访问同一个变量的时候,会产生共享变量的问题 解决变量
锁,信号灯 锁(Lock):
是一个标志,表示一个线程在占用一些资源 使用方法
锁谁:哪个资源需要多个线程共享,锁哪个 理解锁:锁其实不是锁住谁,而是一个令牌
线程安全问题:
如果一个变量/资源,他对于多线程来讲,不用加锁也不会引起任何问题,则成为线程安全 线程不安全变量类型:list, set, dict 线程安全变量类型:queue
生产者消费者问题
一个模型,可以用来搭建消息队列 queue是一个用来存放变量的数据结构,特点是先进先出,内部元素排队,可以理解成一个特殊的list
import threading
sum = 0
loopSum = 1000000
def myAdd ( ) :
global sum , loopSum
for i in range ( 1 , loopSum) :
sum += 1
def myMinu ( ) :
global sum , loopSum
for i in range ( 1 , loopSum) :
sum -= 1
if __name__ == '__main__' :
print ( "Starting ....{0}" . format ( sum ) )
t1 = threading. Thread( target= myAdd, args= ( ) )
t2 = threading. Thread( target= myMinu, args= ( ) )
t1. start( )
t2. start( )
t1. join( )
t2. join( )
print ( "Done .... {0}" . format ( sum ) )
Starting ....0
Done .... -11539
import threading
sum = 0
loopSum = 1000000
lock = threading. Lock( )
def myAdd ( ) :
global sum , loopSum
for i in range ( 1 , loopSum) :
lock. acquire( )
sum += 1
lock. release( )
def myMinu ( ) :
global sum , loopSum
for i in range ( 1 , loopSum) :
lock. acquire( )
sum -= 1
lock. release( )
if __name__ == '__main__' :
print ( "Starting ....{0}" . format ( sum ) )
t1 = threading. Thread( target= myAdd, args= ( ) )
t2 = threading. Thread( target= myMinu, args= ( ) )
t1. start( )
t2. start( )
t1. join( )
t2. join( )
print ( "Done .... {0}" . format ( sum ) )
Starting ....0
Done .... 0
import threading
import time
import queue
class Producer ( threading. Thread) :
def run ( self) :
global queue
count = 0
while True :
if queue. qsize( ) < 1000 :
for i in range ( 100 ) :
count = count + 1
msg = '生成产品' + str ( count)
queue. put( msg)
print ( msg)
time. sleep( 0.5 )
class Consumer ( threading. Thread) :
def run ( self) :
global queue
while True :
if queue. qsize( ) > 100 :
for i in range ( 3 ) :
msg = self. name + '消费了 ' + queue. get( )
print ( msg)
time. sleep( 1 )
if __name__ == '__main__' :
queue = queue. Queue( )
for i in range ( 500 ) :
queue. put( '初始产品' + str ( i) )
for i in range ( 2 ) :
p = Producer( )
p. start( )
for i in range ( 5 ) :
c = Consumer( )
c. start( )
import threading
import time
lock_1 = threading. Lock( )
lock_2 = threading. Lock( )
def func_1 ( ) :
print ( "func_1 starting........." )
lock_1. acquire( )
print ( "func_1 申请了 lock_1...." )
time. sleep( 2 )
print ( "func_1 等待 lock_2......." )
lock_2. acquire( )
print ( "func_1 申请了 lock_2......." )
lock_2. release( )
print ( "func_1 释放了 lock_2" )
lock_1. release( )
print ( "func_1 释放了 lock_1" )
print ( "func_1 done.........." )
def func_2 ( ) :
print ( "func_2 starting........." )
lock_2. acquire( )
print ( "func_2 申请了 lock_2...." )
time. sleep( 4 )
print ( "func_2 等待 lock_1......." )
lock_1. acquire( )
print ( "func_2 申请了 lock_1......." )
lock_1. release( )
print ( "func_2 释放了 lock_1" )
lock_2. release( )
print ( "func_2 释放了 lock_2" )
print ( "func_2 done.........." )
if __name__ == "__main__" :
print ( "主程序启动.............." )
t1 = threading. Thread( target= func_1, args= ( ) )
t2 = threading. Thread( target= func_2, args= ( ) )
t1. start( )
t2. start( )
t1. join( )
t2. join( )
print ( "主程序启动.............." )
主程序启动..............
func_1 starting.........
func_2 starting.........
func_2 申请了 lock_2....
func_1 申请了 lock_1....
func_1 等待 lock_2.......
func_2 等待 lock_1.......
import threading
import time
lock_1 = threading. Lock( )
lock_2 = threading. Lock( )
def func_1 ( ) :
print ( "func_1 starting........." )
lock_1. acquire( timeout= 4 )
print ( "func_1 申请了 lock_1...." )
time. sleep( 2 )
print ( "func_1 等待 lock_2......." )
rst = lock_2. acquire( timeout= 2 )
if rst:
print ( "func_1 已经得到锁 lock_2" )
lock_2. release( )
print ( "func_1 释放了锁 lock_2" )
else :
print ( "func_1 注定没申请到lock_2....." )
lock_1. release( )
print ( "func_1 释放了 lock_1" )
print ( "func_1 done.........." )
def func_2 ( ) :
print ( "func_2 starting........." )
lock_2. acquire( )
print ( "func_2 申请了 lock_2...." )
time. sleep( 4 )
print ( "func_2 等待 lock_1......." )
lock_1. acquire( )
print ( "func_2 申请了 lock_1......." )
lock_1. release( )
print ( "func_2 释放了 lock_1" )
lock_2. release( )
print ( "func_2 释放了 lock_2" )
print ( "func_2 done.........." )
if __name__ == "__main__" :
print ( "主程序启动.............." )
t1 = threading. Thread( target= func_1, args= ( ) )
t2 = threading. Thread( target= func_2, args= ( ) )
t1. start( )
t2. start( )
t1. join( )
t2. join( )
print ( "主程序结束.............." )
import threading
import time
semaphore = threading. Semaphore( 3 )
def func ( ) :
if semaphore. acquire( ) :
for i in range ( 5 ) :
print ( threading. currentThread( ) . getName( ) + ' get semaphore' )
time. sleep( 15 )
semaphore. release( )
print ( threading. currentThread( ) . getName( ) + ' release semaphore' )
for i in range ( 8 ) :
t1 = threading. Thread( target= func)
t1. start( )
import threading
import time
def func ( ) :
print ( "I am running........." )
time. sleep( 4 )
print ( "I am done......" )
if __name__ == "__main__" :
t = threading. Timer( 6 , func)
t. start( )
i = 0
while True :
print ( "{0}***************" . format ( i) )
time. sleep( 3 )
i += 1
可重入锁
一个锁,可以被一个线程多次申请 主要解决递归调用的时候,需要申请锁的情况
import threading
import time
class MyThread ( threading. Thread) :
def run ( self) :
global num
time. sleep( 1 )
if mutex. acquire( 1 ) :
num = num+ 1
msg = self. name+ ' set num to ' + str ( num)
print ( msg)
mutex. acquire( )
mutex. release( )
mutex. release( )
num = 0
mutex = threading. RLock( )
def testTh ( ) :
for i in range ( 5 ) :
t = MyThread( )
t. start( )
if __name__ == '__main__' :
testTh( )