python基础(线程的概述,创建与使用)
一、 线程与进程的比较:
1.1 线程与进程:
线程:
线程是进程中的一个单位
线程是计算机中被CPU调度的最小单位,开销小
轻型进程 轻量级的进程
在同一个进程中的多个线程是可以共享公有数据
线程的开启\销毁\切换都比进程要高效很多
进程:
计算机中最小的资源分配单位
数据隔离 开销大
1.2 为什么要使用线程:
开启进程 关闭进程 切换进程都需要时间
你的电脑的资源还是有限的
开启过多的进程会导致你的计算机崩溃
多个进程与多个线程都可以利用多核(多个CPU)处理数据
1.3 python当中的多线程:
不能访问多个cpu,是Cpython解释器导致
Cpython解释器存在全局解释器锁(GIL-Global Interpreter Lock),导致了同一时刻只能有一个线程访问CPU
jpython pypy解释器中的多线程是可以访问多核(多个CPU)
二、 dis模块:
查看Python解释器运行的底层代码块对应的字节码指令序列
示例:
# 示例: from dis import dis def func(): a =[] a.append(1) dis(func)
三、 创建线程:
# 示例(无参数): import os import time from threading import Thread def func(): time.sleep(1) print('in func', os.getpid()) print('in main', os.getpid()) for i in range(10): Thread(target=func).start() # 创建10个线程
# 示例(参数): # 创建10个子线程: import os import time from threading import Thread def func(i): # 子线程函数 time.sleep(1) print('in func', i, os.getpid()) print('in main', os.getpid()) for i in range(20): Thread(target=func, args=(i,)).start() # i通过args参数传递到自线程
四、 进程与线程之间的内存开销比较:
主线程是在进程中创建多个子线程,开销小
主进程会创建多个子进程,开销大
# 线程与进程之间的开销: import time from multiprocessing import Process from threading import Thread def func(a): a += 1 if __name__ == '__main__': t_start = time.time() # 线程的开启时间 t_l = [] for i in range(100): t = Thread(target=func, args=(i,)) t.start() t_l.append(t) for t in t_l: t.join() print('thread :', time.time() - t_start) # 线程的时间差 thread : 0.03014397621154785 p_start = time.time() # 进程的开启时间 p_l = [] for i in range(100): p = Process(target=func, args=(i,)) p.start() p_l.append(t) for p in p_l: t.join() print('Process', time.time() - p_start) # 进程的时间差 Process 2.994523525238037
五、 进程与线程在内存中的数据分配:
线程之间共有数据共享
进程中数据都是私有,不共享
# 线程与线程和进程与进程之间数据使用比较: # 多个线程之间的全局变量是共享的: from threading import Thread tn = 0 # 全局变量 def func(): global tn tn += 1 t_l = [] for i in range(100): t = Thread(target=func) t.start() t_l.append(t) for t in t_l: t.join() print("Thread: ", tn) # Thread: 100 # 进程之间数据隔离: # 进程之间的数据不能共享,在子进程中数据的修改不能改变全局变量的值(可以通过Manager类修改) from multiprocessing import Process pn = 0 # 全局变量 def func(): global pn pn += 1 if __name__ == '__main__': p_l = [] for i in range(100): p = Process(target=func) p.start() p_l.append(p) for p in p_l: p.join() print("Process: ", pn) # Process: 0
六、 线程的其他方法:
6.1 active_count类:
线程没有terminate 不能强制结束,主线程等待直到子线程结束
active_count(): 查看当前正在工作的线程个数
# 示例: import os import time from threading import Thread, active_count def func(): time.sleep(2) print('in func', os.getpid()) for i in range(10): Thread(target=func).start() print(active_count()) # 11
6. 2 currentThread, activeCount, enumerate类方法:
# currentThread类: # currentThread().name :查看线程名 # currentThread().ident :查看线程号 # 示例: import os from threading import Thread, currentThread, activeCount, enumerate def func(): t = currentThread() print(t.getName()) # 查看线程名:Thread-1 t.setName('AAA') # 设置线程名:AAA print(t.name, t.ident, os.getpid()) # Thread-1 7832 1960 (子线程) tobj = Thread(target=func) tobj.start() print('tobj :', tobj) # tobj : <Thread(Thread-1, started 7832)> t2 = currentThread() print(t2.name, t2.ident, os.getpid()) # MainThread 17672 1960 (主线程) print('主线程...') print(t2.is_alive()) # 查看线程是否还存活 print(activeCount()) # 返回正在运行的线程数量, 与len(threading.enumerate())有相同的结果 print(enumerate()) # 返回一个正在运行的所有线程的列表
https://www.cnblogs.com/WiseAdministrator/