今天我们来介绍多线程。
进程里有很多目标,多线程的目的简言之就是加快进程,提高效率,多个操作同时进行。
下面来看代码:
一.初识
import time
import threading
###############单线程##############################
def coding():
for x in range(3):
print("正在玩孙尚香%s"%x)
time.sleep(1)
def codis():
for x in range(3):
print("正在玩孙权%s" %x)
time.sleep(1)
def main():
coding()
codis()
if __name__ == '__main__':
main()
######3##############多线程###########################
def coding():
for x in range(3):
print("正在玩孙尚香%s" % threading.current_thread())#打印当前线程的名字
time.sleep(1)
def codis():
for x in range(3):
print("正在玩孙权%s" % threading.current_thread())#打印当前线程的名字
time.sleep(1)
def main():
t1=threading.Thread(target=coding)#创建线程
t2=threading.Thread(target=codis)#创建线程
t1.start()
t2.start()
print(threading.enumerate())#打印所有线程的名字
if __name__ == '__main__':
main()
#二.使用thread类创建多线程
#二.使用thread类创建多线程
class CodingThread(threading.Thread):
# def run(self):
# for x in range(3):
# print("正在玩孙尚香%s" % threading.current_thread()) # 打印当前线程的名字
time.sleep(1)
class DrawThread(threading.Thread):
def run(self):
for x in range(3):
print("正在玩孙权%s" % threading.current_thread())
time.sleep(1)
def main():
t1=CodingThread()
t2=DrawThread()
t1.start()
t2.start()
if __name__ == '__main__':
main()
三.多线程共享全局变量及锁机制
VALUE=0
gLook=threading.Lock()#锁机制1
def add_value():
global VALUE
gLook.acquire()#锁机制2
for x in range(10000000):
VALUE+=1
gLook.release()#锁机制3
print(VALUE)
def main():
for x in range(2):
t1=threading.Thread(target=add_value)
t1.start()
if __name__ == '__main__':
main()
四.多线程实例(生产者与消费者模式)
lock版本
import time
import threading
import random
gMoney=1000
gLock=threading.Lock()
gtotalTimes=10
gTime=0
class Producer(threading.Thread):
def run(self):
global gMoney
global gTime
while True:
money=random.randint(100,1000)
gLock.acquire()
if gTime>=gtotalTimes:
gLock.release()
break
gMoney+=money
print('%s生产了%d元,剩余%d元钱'%(threading.current_thread(),money,gMoney))
gTime+=1
gLock.release()
time.sleep(0.5)
class Consumer(threading.Thread):
def run(self):
global gMoney
while True:
money=random.randint(100,1000)
gLock.acquire()
if gMoney>=money:
gMoney-=money
print("%s消费了%d元,剩余%d元"%(threading.current_thread(),money,gMoney))
else:
if gTime>=gtotalTimes:
gLock.release()
break
print('%s消费者准备消费%d元,剩余%d元,不足!'%(threading.current_thread(),money,gMoney))
gLock.release()
time.sleep(0.5)
def main():
for x in range(3):
t=Consumer(name='消费者线程%d'%x)
t.start()
for x in range(5):
t=Producer(name='生产者线程%d'%x)
t.start()
if __name__ == '__main__':
main()
五.condition版本的消费者和生产者模式。
为了克服lock版本对cpu的损耗,我们采用threading.condition
1.acquire上锁
2.release解锁
3.wait:将该线程处于等待状态,并且会释放锁,可以被notify,notify_all唤醒。
4.notify通知某个在等待进程,默认为第一个。
5.notify_all:通知所有在等待的进程,并且notify_all和notify不会解锁,应该啊在release前调用。
下面来看代码:
import time
import threading
import random
gMoney=1000
gCondition=threading.Condition()
gtotalTimes=10
gTime=0
class Producer(threading.Thread):
def run(self):
global gMoney
global gTime
while True:
money=random.randint(100,1000)
gCondition.acquire()
if gTime>=gtotalTimes:
gCondition.release()
break
gMoney+=money
print('%s生产了%d元,剩余%d元钱'%(threading.current_thread(),money,gMoney))
gTime+=1
gCondition.notify_all()#通知苏醒
gCondition.release()
time.sleep(0.5)
class Consumer(threading.Thread):
def run(self):
global gMoney
while True:
money=random.randint(100,1000)
gCondition.acquire()
while gMoney<money:
if gTime>=gtotalTimes:
return
print("%s准备消费%d元,剩余%d元,不足!"%(threading.current_thread(),money,gMoney))
gCondition.wait()
print('%s消费了%d元,剩余%d元'%(threading.current_thread(),money,gMoney))
gCondition.release()
time.sleep(0.5)
def main():
for x in range(3):
t=Consumer(name='消费者线程%d'%x)
t.start()
for x in range(5):
t=Producer(name='生产者线程%d'%x)
t.start()
if __name__ == '__main__':
main()
Queue线程安全队列
加锁是个经常的过程,如果你想把一些数据存储到某个队列,python内置queue模块,其中Queue(先进先出),LiFoQueue(后进先出),可在多线程中使用,实现线程的同步。
1.q=Queue(3)#初始化创建一个先进先出队列。
2.qsize(),返回队列的大小。
3.empty()判断是否为空。
4.full() 判断是否满。
5.get() 按队列规则取出数据。
6.put(),将数据放入队列中。
下面看代码:
from queue import Queue
import time
import threading
q=Queue(4)
# print(q.qsize())
# print(q.empty())
# for x in range(4):
# q.put(x)
# print()
# print(q.full())
# for x in range(4):
# print(q.get())
def set_value(q):
index=0
while True:
q.put(index)
index+=1
time.sleep(3)
def get_valuee(q):
while True:
print(q.get())
def main():
q=Queue(4)
t1=threading.Thread(target=set_value,args=[q])
t2=threading.Thread(target=get_valuee,args=[q])
t1.start()
t2.start()
if __name__ == '__main__':
main()