注:這篇文章部分為廖雪峰py3教程:點我,本文使用python3.5
(1)thread模塊不支持守護線程,守護線程表示這個線程不是重要的,進程退出時不需要等待這個線程執行完成。在python的另一個模塊threading中支持守護線程。
(2)threading.current_thread().name:獲取當前線程的名字
(3)線程實例.start():線程開始執行
(4)線程實例.join():等待目前正在執行的線程執行完畢
(5)線程實例.daemon = True:設置該線程為守護線程
例子一:
import timeimport threadingdef run_func(): print('[+]thread %s is running...' % threading.current_thread().name) cnt = 0 while cnt < 5: cnt += 1 print('thread %s >>> %s' % (threading.current_thread().name, cnt)) time.sleep(1) print('thread %s ended' % threading.current_thread().name)if __name__ == '__main__': print('thread %s is running..' % threading.current_thread().name) t = threading.Thread(target=run_func, name='LoopThread') t.start() t.join() print('[+]thread %s ended' % threading.current_thread().name)例子二:import threadingimport timedef func(slp): name = threading.current_thread().name print('[+]thread%s start at ' % name, time.ctime()) time.sleep(slp) print('[+]thread%s end at ' % name, time.ctime())if __name__ == '__main__': trds = list() slps = [x*2 for x in range(1, 5)] for each in range(4): trds.append(threading.Thread(target=func, args=(slps[each], ))) print('[+]main time start at', time.ctime()) for each in trds: each.start() for each in trds: each.join() print('[+]main time end at ', time.ctime())'''output:[+]main time start at Sun Feb 5 17:02:13 2017[+]threadThread-1 start at Sun Feb 5 17:02:13 2017[+]threadThread-2 start at Sun Feb 5 17:02:13 2017[+]threadThread-3 start at Sun Feb 5 17:02:13 2017[+]threadThread-4 start at Sun Feb 5 17:02:13 2017[+]threadThread-1 end at Sun Feb 5 17:02:15 2017[+]threadThread-2 end at Sun Feb 5 17:02:17 2017[+]threadThread-3 end at Sun Feb 5 17:02:19 2017[+]threadThread-4 end at Sun Feb 5 17:02:21 2017[+]main time end at Sun Feb 5 17:02:21 2017'''import threadingimport timedef func(output, sleeptime):    print('[+]start at', time.ctime())    print('%s' % threading.current_thread().name, output)    time.sleep(sleeptime)    print('[+]end at', time.ctime())if __name__ == '__main__':    sleeptime = 5    thr = threading.Thread(name='lrh', target=func, args=('test now...', sleeptime))    thr.daemon = True    thr.start()    '''#設置為守護線程后,程序執行完thr.start()后就開始退出,#由于執行了sleep(),輸出是不會同時有start at 時間,end at 時間的 #output:[+]start at Thu Feb 16 17:40:07 2017'''線程鎖
進程之間的變量是拷貝的,而線程是共用變量,所有當多個線程存在時需要限制其他線程不能使用,僅某個線程可以使用,這就是線程鎖,import threadingimport osimport timeimport randombalance = 0lock = threading.Lock()def run_func(n):    global balance    balance = balance + n    balance = balance - ndef run_thread(n):    for each in range(10000):        lock.acquire()        try:            run_func(n)        except Exception as error:            print(error)        finally:            lock.release()t1 = threading.Thread(target=run_thread, args=(5000099,))t2 = threading.Thread(target=run_thread, args=(100000,))t1.start()t2.start()t1.join()t2.join()print(balance)多個線程執行lock.acquire()時,只有一個線程能成功的獲取鎖,其他線程只能等待,所以一定要記得釋放鎖此外,在python中可以使用上下文管理,即使用with語句。多核cpu:
import threadingimport multiprocessingdef loop():    x = 0    while True:        x = x ^ 1for i in range(multiprocessing.cpu_count()):    t = threading.Thread(target=loop)    t.start()由于GIL全局鎖把所有的線程的執行上了鎖,多線程在python中只能交替的運行,即使100個線程跑在100核cpu上,也只能用到一個核ThreadLocal,解決多線程局部變量的傳遞問題
由于線程之間的全局變量是共用的,所以對于一個線程來說,使用局部變量是最好的,避免影響其他線程之間的變量,那么就會有一個問題,局部變量在傳遞起來就會比較麻煩一個可行的思路是使用線程名字作為key,value來存放待傳遞變量python給我們提供了更加方便的做法,使用ThreadLocalimport threadinglocalSet = threading.local()def func_run():    std = localSet.student    print('Hello, %s (in %s)' % (std, threading.current_thread().name))def thread_run(name):    localSet.student = name    func_run()if __name__ == '__main__':    t1 = threading.Thread(target=thread_run, args=('lrh', ), name='Thread-A')    t2 = threading.Thread(target=thread_run, args=('kch',), name='Thread-B')    t1.start()    t2.start()    t1.join()    t2.join()
新聞熱點
疑難解答