一.進(jìn)程和線程的意義
1.進(jìn)程: 正在執(zhí)行的程序
特點: 相互獨立 占用受保護(hù)獨立的內(nèi)存單元
2.線程: 進(jìn)程想要執(zhí)行任務(wù),必須的有線程
一個進(jìn)程的所有認(rèn)為都是在線程中進(jìn)行的
特點: 串行(一個一個按順序去執(zhí)行任務(wù))
3.多線程
特點: 并行(每條線程可以同時執(zhí)行不同的任務(wù))
原理:
1.同一時間,cpu只能處理一條線程, 只有一條線程在工作.
2.多線程并發(fā)執(zhí)行,其實是cpu在快速地在多線程之間調(diào)度.
3.cpu調(diào)度線程的時間足夠快,造成了多線程并發(fā)的假象.
二.耗時操作
一個進(jìn)程默認(rèn)有一個線程,這個線程叫主線程.
默認(rèn)情況下, 所有的代碼都是在主線程里面進(jìn)行的.
import time, datetime.
def down_load(film_name):
print('開始下載%s' % film_name, '開始時間:%s' % datetime.datetime.now())
time.sleep(5) # 程序執(zhí)行到這個地方,線程會阻塞5秒,再執(zhí)行后面膜的代碼
print('%s 下載結(jié)束' % film_name,'結(jié)束時間:%s' % datetime.datetime.now())
if __name__ == '__main__':
down_load('小黃人')
down_load('地心歷險記')
三.多線程方法1:通過Thread類創(chuàng)建子線程
python通過threading模塊
默認(rèn)創(chuàng)建的線程叫主線程, 自己創(chuàng)建的線程叫子線程
如果希望代碼在子線程里面執(zhí)行,必須手動創(chuàng)建子線程對象
import threading
import time, datetime
def down_load(film_name):
print('開始下載%s' % film_name, '開始時間:%s' % datetime.datetime.now())
time.sleep(5) # 程序執(zhí)行到這個地方,線程會阻塞5秒,再執(zhí)行后面膜的代碼
print('%s 下載結(jié)束' % film_name,'結(jié)束時間:%s' % datetime.datetime.now())
print('下載%s' % film_name, threading.current_thread())
if __name__ == '__main__':
# down_load('小黃人')
# 1.創(chuàng)建線程對象
"""
Thread - 線程類
Thread(target=函數(shù)名, args=參數(shù)列表) - 直接創(chuàng)建線程對象
函數(shù)名 = 需要在當(dāng)前線程執(zhí)行的函數(shù)變量
參數(shù)列表(要求是元組) = 元祖, 元祖的元素是函數(shù)的參數(shù)
"""
t1 = threading.Thread(target=down_load, args=('小黃人',))
t2 = threading.Thread(target=down_load, args=('小綠人',))
# 2. 在子線程中執(zhí)行任務(wù)
"""
這里是調(diào)用down_load函數(shù),并且傳遞一個參數(shù)'小黃人'
"""
t1.start()
t2.start()
四.多線程方法2: 通過Thread的子類創(chuàng)建子線程.
import datetime, time, threading
"""
除了直接創(chuàng)建Thread的對象,還可以繼承這個類的對象
注意: 一個進(jìn)程中有多個線程,進(jìn)程會在所有的線程都結(jié)束才會結(jié)束
線程中的任務(wù)執(zhí)行完了,線程就結(jié)束
"""
class Thread1(threading.Thread):
def __init__(self, film_name):
super().__init__()
self.film_name = film_name
# 2.重寫run方法
def run(self):
print('開始下載%s' % self.film_name , '開始時間:%s' % datetime.datetime.now())
time.sleep(5) # 程序執(zhí)行到這個地方,線程會阻塞5秒,再執(zhí)行后面膜的代碼
print('%s 下載結(jié)束' % self.film_name , '結(jié)束時間:%s' % datetime.datetime.now())
print(threading.current_thread())
# 創(chuàng)建線程對象
t1 = Thread1('小黃人')
# 4.通過線程對象調(diào)用start在子線程重執(zhí)行run方法
t1.start()
# 直接調(diào)用run方法會在主線程執(zhí)行
五.join函數(shù)
"""
線程對象.join() - 等待線程對象中的任務(wù)執(zhí)行完成
"""
from threading import Thread
import datetime, time, random
class DownLoad(Thread):
def __init__(self, film_name):
super().__init__()
self.film_name = film_name
def run(self):
print('開始下載%s'% self.film_name)
a = random.randint(5,12)
time.sleep(a)
print('下載結(jié)束%s' % self.film_name, '耗時%d秒'% a)
if __name__ == '__main__':
t1 = DownLoad('小黃人')
t2 = DownLoad('小綠人')
time1 = time.time()
t1.start()
t2.start()
# t1和t2的任務(wù)都執(zhí)行完成后才會執(zhí)行后面的代碼
t1.join()
t2.join()
time2 = time.time()
print('總共時間:',str(time2 - time1) + '秒')