1、單執行緒
import解釋:url順序的被請求time
import
urllib2
defget_responses():
urls =[
'','',
'','',
'']start =time.time()
for url in
urls:
url resp =urllib2.urlopen(url)
resp.getcode()
"elapsed time: %s
" % (time.time()-start)
get_responses()
除非cpu從乙個url獲得了回應,否則不會去請求下乙個url
網路請求會花費較長的時間,所以cpu在等待網路請求的返回時間內一直處於閒置狀態。
2、多執行緒
import解釋:urllib2
import
time
from threading import
thread
class
geturlthread(thread):
def__init__
(self, url):
self.url =url
super(geturlthread, self).
__init__()
defrun(self):
resp =urllib2.urlopen(self.url)
self.url, resp.getcode()
defget_responses():
urls =[
'',
'',
'',
'',
'']start =time.time()
threads =
for url in
urls:
t =geturlthread(url)
t.start()
for t in
threads:
t.join()
"elapsed time: %s
" % (time.time()-start)
get_responses()
意識到了程式在執行時間上的提公升
我們寫了乙個多執行緒程式來減少cpu的等待時間,當我們在等待乙個執行緒內的網路請求返回時,這時cpu可以切換到其他執行緒去進行其他執行緒內的網路請求。
我們期望乙個執行緒處理乙個url,所以例項化執行緒類的時候我們傳了乙個url。
執行緒執行意味著執行類裡的run()方法。
無論如何我們想每個執行緒必須執行run()。
為每個url建立乙個執行緒並且呼叫start()方法,這告訴了cpu可以執行執行緒中的run()方法了。
我們希望所有的執行緒執行完畢的時候再計算花費的時間,所以呼叫了join()方法。
join()可以通知主線程等待這個執行緒結束後,才可以執行下一條指令。
每個執行緒我們都呼叫了join()方法,所以我們是在所有執行緒執行完畢後計算的執行時間。
關於執行緒:
cpu可能不會在呼叫start()後馬上執行run()方法。
你不能確定run()在不同執行緒建間的執行順序。
對於單獨的乙個執行緒,可以保證run()方法裡的語句是按照順序執行的。
這就是因為執行緒內的url會首先被請求,然後列印出返回的結果。
解決資源競爭
from threading import解釋:lock, thread
lock =lock()
some_var =0
class
incrementthread(thread):
defrun(self):
#we want to read a global variable
#and then increment it
global
some_var
lock.acquire()
read_value =some_var
"some_var in %s is %d
" %(self.name, read_value)
some_var = read_value + 1
"some_var in %s after increment is %d
" %(self.name, some_var)
lock.release()
defuse_increment_thread():
threads =
for i in range(50):
t =incrementthread()
t.start()
for t in
threads:
t.join()
"after 50 modifications, some_var should h**e become 50
"after 50 modifications, some_var is %d
" %(some_var,)
use_increment_thread()
lock 用來防止競爭條件
如果在執行一些操作之前,執行緒t1獲得了鎖。其他的執行緒在t1釋放lock之前,不會執行相同的操作
我們想要確定的是一旦執行緒t1已經讀取了some_var,直到t1完成了修改some_var,其他的執行緒才可以讀取some_var
這樣讀取和修改some_var成了邏輯上的原子操作
加鎖保證操作的原子性
from threading import證明了乙個執行緒不可以修改其他執行緒內部的變數(非全域性變數)。thread, lock
import
time
lock =lock()
class
createlistthread(thread):
defrun(self):
self.entries =
for i in range(10):
time.sleep(0.01)
lock.acquire()
self.entries
lock.release()
defuse_create_list_thread():
for i in range(3):
t =createlistthread()
t.start()
use_create_list_thread()
importmakerequests建立了要開啟多執行緒的函式,以及函式相關引數和**函式,其中**函式可以不寫,default是無,也就是說makerequests只需要2個引數就可以執行;threadpool
import
time
import
urllib2
urls =[
'',
'',
'',
'',
'']defmyrequest(url):
resp =urllib2.urlopen(url)
url, resp.getcode()
deftimecost(request, n):
"elapsed time: %s
" % (time.time()-start)
start =time.time()
pool = threadpool.threadpool(5)
reqs =threadpool.makerequests(myrequest, urls, timecost)
[ pool.putrequest(req)
for req in
reqs ]
pool.wait()
注意:threadpool 是非執行緒安全的。
python中多執行緒 Python之多執行緒
python之多執行緒 一 概念 1 多工可以由多程序完成,也可以由乙個程序內的多執行緒完成。程序是由若干的執行緒組成,乙個程序至少有乙個程序。執行緒是作業系統直接支援的執行單元,天賜高階預壓通常都是內建多執行緒的支援,python的執行緒是真正的posix thread而不是模擬出來的執行緒。2 ...
python中的多執行緒
python中的多執行緒是假的多執行緒!為什麼這麼說,我們先明確乙個概念,全域性直譯器鎖 gil global interpreter lock python 的執行由python虛擬機器 直譯器 來控制,同時只有乙個執行緒在執行 對python虛擬機器的訪問由全域性直譯器鎖 gil 來控制,正是這...
python中的多執行緒
當python程式執行時會預設建立乙個主線程,除了主線程之外我們還可以建立別的執行緒,可以使用threading引入 import threading import time defthinking for i in range 3 threading.current thread 檢視當前正在執行...