7.20 python线程3
2018-7-20 18:46:49 去俺弟家玩去 后天回来
1.复习
# !/usr/bin/env python # !--*--coding:utf-8 --*-- # !@Time :2018/7/20 8:56 # !@Author TrueNewBee # 正确的学习方法 # input # output # correct 纠正 # 线程: # 1.线程是进程中的执行单位 # 2.线程是cpu执行的最小单位 # 3.线程之间资源共享 # 4.线程的开启和关闭以及切换的时间开销远远小于进程 # 5.线程本身可以在同一时间使用多个cpu # python 与 线程 # CPython解释器在解释代码过程中容易产生数据不安全的问题 # GIL全局解释器锁 锁的是线程 # threading
2.守护线程
# !/usr/bin/env python # !--*--coding:utf-8 --*-- # !@Time :2018/7/20 9:04 # !@Author TrueNewBee import time from threading import Thread def func1(): while True: print('*'*10) time.sleep(1) def func2(): print('in func2') time.sleep(5) if __name__ == '__main__': t = Thread(target=func1, ) t.daemon = True t.start() t2 = Thread(target=func2, ) t2.start() t2.join() print('主线程') # 守护进程随着主进程代码的结束而结束(进程间资源不共享,所以想咋结束咋结束) # 守护线程会在主线程结束之后等待其他子线程的结束才结束(线程间资源共享,所以不能主线程不能立马结束) # 主进程在执行完自己的代码之后不会立即结束,而是等待子进程结束之后 挥手子进程的资源 # import time # from multiprocessing import Process # # # def func(): # time.sleep(5) # # # if __name__ == '__main__': # Process(target=func, ).start()
3.锁
# !/usr/bin/env python # !--*--coding:utf-8 --*-- # !@Time :2018/7/20 9:29 # !@Author TrueNewBee # import time # from threading import Thread, Lock # def func(lock1): # global n # lock1.acquire() # 加上一个锁 # # n = 1 python内部就是下面执行的 # temp = n # time.sleep(0.2) # n = temp - 1 # 9 刚取回来还没来得及赋值又被别人拿走了,所以得自己加个锁不让被人拿走 # lock1.release() # 换钥匙 # # # n = 10 # t_list = [] # lock = Lock() # for i in range(10): # t = Thread(target=func, args=(lock, )) # t.start() # t_list.append(t) # for t in t_list: # t.join() # print(n) # 不加锁是9 加锁是 0 # 科学家吃面问题 经典死锁问题 # noodle_lock = Lock() # fork_lock = Lock() # 互斥锁 # # # def eat1(name): # noodle_lock.acquire() # print('%s拿到面条啦' % name) # fork_lock.acquire() # print('%s拿到叉子啦' % name) # print('%s吃面' % name) # fork_lock.release() # noodle_lock.release() # # # def eat2(name): # fork_lock.acquire() # print('%s拿到叉子啦' % name) # time.sleep(1) # noodle_lock.acquire() # print('%s拿到面条啦' % name) # print('吃面') # noodle_lock.release() # fork_lock.release() # # # if __name__ == '__main__': # Thread(target=eat1, args=('alex', )).start() # Thread(target=eat2, args=('Egon',)).start() # Thread(target=eat1, args=('bossJin',)).start() # Thread(target=eat2, args=('zeZha',)).start() import time from threading import RLock, Thread fork_lock = noodle_lock = RLock() # 一个钥匙串上的两把钥匙 # 递归锁 为了解决死锁问题,可以acquire()多次, def eat1(name): noodle_lock.acquire() # 一把钥匙 print('%s拿到面条啦' % name) fork_lock.acquire() print('%s拿到叉子啦' % name) print('%s吃面' % name) fork_lock.release() noodle_lock.release() def eat2(name): fork_lock.acquire() print('%s拿到叉子啦' % name) time.sleep(1) noodle_lock.acquire() print('%s拿到面条啦' % name) print('%s吃面' % name) noodle_lock.release() fork_lock.release() if __name__ == '__main__': Thread(target=eat1, args=('alex', )).start() Thread(target=eat2, args=('Egon',)).start() Thread(target=eat1, args=('bossJin',)).start() Thread(target=eat2, args=('zeZha',)).start()
4.条件和定时器
# !/usr/bin/env python # !--*--coding:utf-8 --*-- # !@Time :2018/7/20 11:25 # !@Author TrueNewBee import time from threading import Semaphore, Thread def func(sem1, a, b): # 同一时间就让四个线程执行代码 sem1.acquire() time.sleep(1) print(a+b) sem1.release() if __name__ == '__main__': sem = Semaphore(4) for i in range(10): t = Thread(target=func, args=(sem, i, i+5)) t.start()
5.事件
# !/usr/bin/env python # !--*--coding:utf-8 --*-- # !@Time :2018/7/20 11:31 # !@Author TrueNewBee # 事件被创建的时候 # False状态 # wait() 阻塞 # True状态 # wait() 非阻塞 # clear 设置状态为False # set 设置状态为True # 数据库- 文件夹 # 文件夹里有好多excel表格 # 1.能够更方便的对数据进行增删改查 # 2.安全访问的机制 # 伪代码 看现象: # 起两个线程 # 第一个线程:连接数据库 # 等待一个信号,告诉我我们之间的网络是通的 # 连接数据库 # 第二个线程:检测与数据库之间的网络情况是否连通 # time.sleep(0,2) # 将事件状态设置为True import time import random from threading import Thread, Event def connect_db(e1): count = 0 while count < 3: # 连接三次 e1.wait(0.5) # 状态是False的时候,我只等待1s if e1.is_set() == True: print('连接成功') break else: count += 1 print('第%s次连接失败' % count) else: # 连接三次都都没连上,主动抛出异常 raise TimeoutError('数据库连接超时') def check_web(e2): time.sleep(random.randint(0, 3)) e2.set() if __name__ == '__main__': e = Event() t1 = Thread(target=connect_db, args=(e, )) t2 = Thread(target=check_web, args=(e, )) t1.start() t2.start()