Python快速學習第十一天--Python多線程

Python中使用線程有三種方式:

方法一:函數式

調用thread模塊中的start_new_thread()函數來產生新線程。語法如下:

thread.start_new_thread ( function, args[, kwargs] )

參數說明:

  • function - 線程函數。
  • args - 傳遞給線程函數的參數,他必須是個tuple類型。
  • kwargs - 可選參數。

實例:

線程的結束一般依靠線程函數的自然結束;也可以在線程函數中調用thread.exit(),他拋出SystemExit exception,達到退出線程的目的。


方法二:通過繼承threading.Thread創建線程

使用Threading模塊創建線程,直接從threading.Thread繼承,然後重寫__init__方法和run方法:

實例



方法三:使用threading.Thread直接在線程中運行函數。

實例:


線程模塊

Python通過兩個標準庫thread和threading提供對線程的支持。thread提供了低級別的、原始的線程以及一個簡單的鎖。

thread 模塊提供的其他方法:

  • threading.currentThread(): 返回當前的線程變量。
  • threading.enumerate(): 返回一個包含正在運行的線程的list。正在運行指線程啓動後、結束前,不包括啓動前和終止後的線程。
  • threading.activeCount(): 返回正在運行的線程數量,與len(threading.enumerate())有相同的結果。

除了使用方法外,線程模塊同樣提供了Thread類來處理線程,Thread類提供了以下方法:

  • run(): 用以表示線程活動的方法。
  • start():啓動線程活動。

  • join([time]): 等待至線程中止。這阻塞調用線程直至線程的join() 方法被調用中止-正常退出或者拋出未處理的異常-或者是可選的超時發生。
  • isAlive(): 返回線程是否活動的。
  • getName(): 返回線程名。
  • setName(): 設置線程名。
  • setDaemon方法。

    在腳本運行的過程中有一個主線程,如果主線程又創建了一個子線程,那麼當主線程退出時,會檢驗子線程是否完成。如果子線程未完成,則主線程會在等待子線程完成後退出。

    當需要主線程退出時,不管子線程是否完成都隨主線程退出,則可以使用Thread對象的setDaemon方法來設置。


線程同步

1.簡單的線程同步

使用Thread對象的Lock和RLock可以實現簡單的線程同步。對於如果需要每次只有一個線程操作的數據,可以將操作過程放在acquire方法和release方法之間。如:

實例:


結果將是輸出10個30。30是x的最終值,由於x是全局變量,每個線程對其操作後進入休眠狀態,在線程休眠的時候,python解釋器就執行了其他的線程而是x的值增加。當所有線程休眠結束後,x的值已被所有線修改爲了30,因此輸出全部爲30。

下面再看看加鎖的實例



2、使用條件變量保持線程同步。

Python的Condition對象提供了對複製線程同步的支持。使用Condition對象可以在某些事件觸發後才處理數據。Condition對象除了具有acquire方法和release的方法外,還有wait方法、notify方法、notifyAll方法等用於條件處理。

實例:




線程間通信:

Event對象用於線程間的相互通信。他提供了設置信號、清除信宏、等待等用於實現線程間的通信。

1、設置信號。Event對象使用了set()方法後,isSet()方法返回真。

2、清除信號。使用Event對象的clear()方法後,isSet()方法返回爲假。

3、等待。當Event對象的內部信號標誌爲假時,則wait()方法一直等到其爲真時才返回。還可以向wait傳遞參數,設定最長的等待時間。

實例:




線程優先級隊列( Queue)


Python的Queue模塊中提供了同步的、線程安全的隊列類,包括FIFO(先入先出)隊列Queue,LIFO(後入先出)隊列LifoQueue,和優先級隊列PriorityQueue。這些隊列都實現了鎖原語,能夠在多線程中直接使用。可以使用隊列來實現線程間的同步。

Queue模塊中的常用方法:

  • Queue.qsize() 返回隊列的大小
  • Queue.empty() 如果隊列爲空,返回True,反之False
  • Queue.full() 如果隊列滿了,返回True,反之False
  • Queue.full 與 maxsize 大小對應
  • Queue.get([block[, timeout]])獲取隊列,timeout等待時間
  • Queue.get_nowait() 相當Queue.get(False)
  • Queue.put(item) 寫入隊列,timeout等待時間
  • Queue.put_nowait(item) 相當Queue.put(item, False)
  • Queue.task_done() 在完成一項工作之後,Queue.task_done()函數向任務已經完成的隊列發送一個信號
  • Queue.join() 實際上意味着等到隊列爲空,再執行別的操作

實例:


發佈了160 篇原創文章 · 獲贊 584 · 訪問量 90萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章