線程的其他方法: from threading import Thread,current_thread: currrent_thread().getName() 獲取線程的名稱 current_thread().ident 獲取到線程的id current_thread() 當前線程的信息 imp ...
線程的其他方法: from threading import Thread,current_thread: currrent_thread().getName() 獲取線程的名稱 current_thread().ident 獲取到線程的id current_thread() 當前線程的信息 import threading #導入threading模塊才能使用下麵的功能: threading.enumerate() 當前正在運行線程對象的列表 threading.active_count() 活動的線程 import time import threading from threading import Thread,current_thread def f1(n): time.sleep(1) print('子線程名稱',current_thread().getName()) print('%s號線程任務' %n) if __name__ == '__main__': t1 =Thread(target=f1,args=(1,)) t1.start() print('主線程名稱',current_thread().getName()) ###MainThread print('主線程ID',current_thread().ident) ##2260 print(current_thread()) #當前線程<_MainThread(MainThread, started 2260)> print(threading.enumerate()) #[<_MainThread(MainThread, started 2260)>, <Thread(Thread-1, started 2520)>] 當前正在運行線程對象的列表 print(threading.active_count()) # 活動的線程 #2 線程池(重點) from concurrent.futures import ThreadPoolExecutor,ProcessPoolExecutor p =ThreadPoolExecutor() 預設的線程個數是cpu個數 *5 p = ProcessPoolExecutor() 預設的進程個數是cup個數(核數) p.map(f1, 可迭代的對象) 非同步執行 def f1(n1,n2): print(n1,n2) p.submit(f1,11,12) res=p.submit(f1,11,12) 非同步提交任務,裡面無敵傳參,但是形參位置必須對應實參接收 res.result() 和get 方法一樣,如果沒有結果,會等待,阻塞程式 shutdown() close+join鎖定線程池,等待線程池中所有已經提交的任務全部執行完畢 import time from threading import current_thread from concurrent.futures import ThreadPoolExecutor,ProcessPoolExecutor def f1(n,s): time.sleep(1) # print('%s號子線程' %current_thread().ident) # print(n,s) return (n,s) if __name__ == '__main__': tp =ThreadPoolExecutor(4) # tp = ProcessPoolExecutor(4) # tp.map(f1,range(10)) #非同步提交任務,參數同樣是任務名稱,可迭代對象 res_list = [] for i in range(10): res = tp.submit(f1,i,'藤椒') #submit是給線程池非同步提交任務 print(res) #res.result() res_list.append(res) # for r in res_list: # print(r.result()) tp.shutdown() #主線程等待所有提交給線程池的任務,全部執行完畢 close+join for r in res_list: print(r.result()) print('主線程結束') 隊列(重點) 先進先出 queue.Queue() 先進先出隊列 q.qsize() 當前內容的長度 q.full() 查看隊列是否滿了 q.empty() 查看隊列是否空了 q.put_nowait() 放入不等待,程式往下執行 q.get_nowait() 獲取不等待,程式往下執行 import queue #先進先出隊列 q =queue.Queue(3) q.put(1) q.put(2) print('當前隊列內容長度',q.qsize()) q.put(3) print('查看隊列是否滿了',q.full()) try: q.put_nowait(4) #報錯queue.Full except Exception: print('隊列滿了') print(q.get()) print(q.get()) print('查看隊列是否為空',q.empty()) print(q.get()) print('查看隊列是否為空',q.empty()) try: q.get_nowait() #queue.Empty except Exception: print('隊列空了') 先進後出,或者後進先出,類似於棧fifo: first in first out queue.LifoQueue() 先進後出\後進先出隊列 import queue q = queue.LifoQueue(3) q.put(1) q.put(2) q.put(3) print(q.get()) print(q.get()) print(q.get()) 優先隊列: queue.PriorityQueue() put的數據是一個元組,元組的第一個參數是優先順序數字,數字越下,優先順序越高,越先被get到被去出來,第二個參數是put進去的值,吐過說優先順序相同,那麼直別忘了應該是相同的數據類型,字典不行 如果優先順序數字相同,會比較第二個參數的元素的ascii表中的位置,如果數據類型不同會報錯. 如果說值裡面的元素是數字類型,那麼兩個值的優先順序相同時,比較的是兩個值得大小,小的優先被去出來. import queue q = queue.PriorityQueue(5) # q.put((5,'alex')) # q.put((2,'寶寶')) # q.put((7,'大力')) # q.put((5,(2,3))) q.put((5,(2,3))) #如果說值裡面的元素是數字類型,那麼當兩個值的優先順序相同時,比較的是兩個值的大小,小的優先被取出來 #如果元素是字元串,那麼依次比較每個字母的ascii表中的位置,小的優先被取出來 # q.put((2,{'x':3})) # q.put((5,(1,2))) q.put((5,(2,2,3))) # q.put((2,'zalex')) # q.put((-1,'yubing')) # q.put((2,{'k':666})) #如果優先順序數字相同,如果數據類型不同會報錯 # q.put((2,('a','b'))) # q.put((1,(1,2))) # q.put((3,(1,2))) # q.put((-10,(1,2))) print(q.get()) 協程:輕量型線程. 生成器,Greenlet模塊,Gevent模塊(重點) 協程:一個線程裡面實現任務的併發:變成生成器(記錄狀態),實現兩個程式的來回切換,實現併發 生成器版協程: import time def f1(): for i in range(10): time.sleep(0.5) print('f1>>',i) yield def f2(): g = f1() for i in range(10): time.sleep(0.5) print('f2>>', i) next(g) f1() f2() Greenlet模塊 如果導入模塊報錯,是沒有載入第三方的模塊,首先:在py解釋器上找到Terminal輸入:pip install greenlet,如果提示不是內部命令,找到python安裝的位置的路徑,Scripts文件裡面的pip,選擇路徑,添加到環境變數裡面(我的電腦--屬性--高級系統設置--環境變數--Path新建添加),在使用管理員命令輸入pip install greenlet,最後重啟解釋器就完成啦,可以開心的使用. import time import greenlet from greenlet import greenlet def f1(s): print('第一次f1'+s) g2.switch('taibai') time.sleep(1) print('第二次f1' + s) g2.switch() def f2(s): print('第一次f2' + s) g1.switch() time.sleep(1) print('第二次f2' + s) g1 = greenlet(f1) g2 = greenlet(f2) g1.switch('alex') Gevent模塊(重點) import gevent from gevent import monkey;monkey.patch_all() import time import threading def f1(): print('第一次f1') # print(threading.current_thread().getName()) # gevent.sleep(1) time.sleep(2) print('第二次f1') def f2(): # print(threading.current_thread().getName()) print('第一次f2') # gevent.sleep(2) time.sleep(2) print('第二次f2') s = time.time() g1 = gevent.spawn(f1) #非同步提交了f1任務 g2 = gevent.spawn(f2) #非同步提交了f2任務 # g1.join() # g2.join() gevent.joinall([g1,g2]) e = time.time() print('執行時間:',e-s) print('主程式任務') 線程池的回調函數 from concurrent.futures import ThreadPoolExecutor,ProcessPoolExecutor def f1(n,s): return n+s def f2(n): print('回調函數>>>',n.result()) if __name__ == '__main__': tp = ThreadPoolExecutor(4) res = tp.submit(f1,11,12).add_done_callback(f2) # print(res.result())
線程的其他方法: from threading import Thread,current_thread: currrent_thread().getName() 獲取線程的名稱 current_thread().ident 獲取到線程的id current_thread() 當前線程的信息 import threading #導入threading模塊才能使用下麵的功能: threading.enumerate() 當前正在運行線程對象的列表 threading.active_count() 活動的線程 import time import threading from threading import Thread,current_thread def f1(n): time.sleep(1) print('子線程名稱',current_thread().getName()) print('%s號線程任務' %n) if __name__ == '__main__': t1 =Thread(target=f1,args=(1,)) t1.start() print('主線程名稱',current_thread().getName()) ###MainThread print('主線程ID',current_thread().ident) ##2260 print(current_thread()) #當前線程<_MainThread(MainThread, started 2260)> print(threading.enumerate()) #[<_MainThread(MainThread, started 2260)>, <Thread(Thread-1, started 2520)>] 當前正在運行線程對象的列表 print(threading.active_count()) # 活動的線程 #2 線程池(重點) from concurrent.futures import ThreadPoolExecutor,ProcessPoolExecutor p =ThreadPoolExecutor() 預設的線程個數是cpu個數 *5 p = ProcessPoolExecutor() 預設的進程個數是cup個數(核數) p.map(f1, 可迭代的對象) 非同步執行 def f1(n1,n2): print(n1,n2) p.submit(f1,11,12) res=p.submit(f1,11,12) 非同步提交任務,裡面無敵傳參,但是形參位置必須對應實參接收 res.result() 和get 方法一樣,如果沒有結果,會等待,阻塞程式 shutdown() close+join鎖定線程池,等待線程池中所有已經提交的任務全部執行完畢 import time from threading import current_thread from concurrent.futures import ThreadPoolExecutor,ProcessPoolExecutor def f1(n,s): time.sleep(1) # print('%s號子線程' %current_thread().ident) # print(n,s) return (n,s) if __name__ == '__main__': tp =ThreadPoolExecutor(4) # tp = ProcessPoolExecutor(4) # tp.map(f1,range(10)) #非同步提交任務,參數同樣是任務名稱,可迭代對象 res_list = [] for i in range(10): res = tp.submit(f1,i,'藤椒') #submit是給線程池非同步提交任務 print(res) #res.result() res_list.append(res) # for r in res_list: # print(r.result()) tp.shutdown() #主線程等待所有提交給線程池的任務,全部執行完畢 close+join for r in res_list: print(r.result()) print('主線程結束') 隊列(重點) 先進先出 queue.Queue() 先進先出隊列 q.qsize() 當前內容的長度 q.full() 查看隊列是否滿了 q.empty() 查看隊列是否空了 q.put_nowait() 放入不等待,程式往下執行 q.get_nowait() 獲取不等待,程式往下執行 import queue #先進先出隊列 q =queue.Queue(3) q.put(1) q.put(2) print('當前隊列內容長度',q.qsize()) q.put(3) print('查看隊列是否滿了',q.full()) try: q.put_nowait(4) #報錯queue.Full except Exception: print('隊列滿了') print(q.get()) print(q.get()) print('查看隊列是否為空',q.empty()) print(q.get()) print('查看隊列是否為空',q.empty()) try: q.get_nowait() #queue.Empty except Exception: print('隊列空了') 先進後出,或者後進先出,類似於棧fifo: first in first out queue.LifoQueue() 先進後出\後進先出隊列 import queue q = queue.LifoQueue(3) q.put(1) q.put(2) q.put(3) print(q.get()) print(q.get()) print(q.get()) 優先隊列: queue.PriorityQueue() put的數據是一個元組,元組的第一個參數是優先順序數字,數字越下,優先順序越高,越先被get到被去出來,第二個參數是put進去的值,吐過說優先順序相同,那麼直別忘了應該是相同的數據類型,字典不行 如果優先順序數字相同,會比較第二個參數的元素的ascii表中的位置,如果數據類型不同會報錯. 如果說值裡面的元素是數字類型,那麼兩個值的優先順序相同時,比較的是兩個值得大小,小的優先被去出來. import queue q = queue.PriorityQueue(5) # q.put((5,'alex')) # q.put((2,'寶寶')) # q.put((7,'大力')) # q.put((5,(2,3))) q.put((5,(2,3))) #如果說值裡面的元素是數字類型,那麼當兩個值的優先順序相同時,比較的是兩個值的大小,小的優先被取出來 #如果元素是字元串,那麼依次比較每個字母的ascii表中的位置,小的優先被取出來 # q.put((2,{'x':3})) # q.put((5,(1,2))) q.put((5,(2,2,3))) # q.put((2,'zalex')) # q.put((-1,'yubing')) # q.put((2,{'k':666})) #如果優先順序數字相同,如果數據類型不同會報錯 # q.put((2,('a','b'))) # q.put((1,(1,2))) # q.put((3,(1,2))) # q.put((-10,(1,2))) print(q.get()) 協程:輕量型線程. 生成器,Greenlet模塊,Gevent模塊(重點) 協程:一個線程裡面實現任務的併發:變成生成器(記錄狀態),實現兩個程式的來回切換,實現併發 生成器版協程: import time def f1(): for i in range(10): time.sleep(0.5) print('f1>>',i) yield def f2(): g = f1() for i in range(10): time.sleep(0.5) print('f2>>', i) next(g) f1() f2() Greenlet模塊 如果導入模塊報錯,是沒有載入第三方的模塊,首先:在py解釋器上找到Terminal輸入:pip install greenlet,如果提示不是內部命令,找到python安裝的位置的路徑,Scripts文件裡面的pip,選擇路徑,添加到環境變數裡面(我的電腦--屬性--高級系統設置--環境變數--Path新建添加),在使用管理員命令輸入pip install greenlet,最後重啟解釋器就完成啦,可以開心的使用. import time import greenlet from greenlet import greenlet def f1(s): print('第一次f1'+s) g2.switch('taibai') time.sleep(1) print('第二次f1' + s) g2.switch() def f2(s): print('第一次f2' + s) g1.switch() time.sleep(1) print('第二次f2' + s) g1 = greenlet(f1) g2 = greenlet(f2) g1.switch('alex') Gevent模塊(重點) import gevent from gevent import monkey;monkey.patch_all() import time import threading def f1(): print('第一次f1') # print(threading.current_thread().getName()) # gevent.sleep(1) time.sleep(2) print('第二次f1') def f2(): # print(threading.current_thread().getName()) print('第一次f2') # gevent.sleep(2) time.sleep(2) print('第二次f2') s = time.time() g1 = gevent.spawn(f1) #非同步提交了f1任務 g2 = gevent.spawn(f2) #非同步提交了f2任務 # g1.join() # g2.join() gevent.joinall([g1,g2]) e = time.time() print('執行時間:',e-s) print('主程式任務') 線程池的回調函數 from concurrent.futures import ThreadPoolExecutor,ProcessPoolExecutor def f1(n,s): return n+s def f2(n): print('回調函數>>>',n.result()) if __name__ == '__main__': tp = ThreadPoolExecutor(4) res = tp.submit(f1,11,12).add_done_callback(f2) # print(res.result())