多任务
目的
在同一时间内执行多个任务
形式
并发 : 在一个时间段内,程序交替的执行
并行 : 多核CPU,同一时间点执行多个任务.每个CPU都有自己的任务
多进程
时间片
操作系统分配给程序执行的一小段时间,只有获得了时间片,程序才能执行
基本知识
每一个程序,默认有一个进程,称为主程序
每一个进程默认有一个线程,称为主线程
进程是操作系统分配资源的最小单位
创建进程
1. 导包 : import multiprocessing
2. 创建进程对象 : multiprocessing.Process(target=函数名)
3. 启动进程 : 进程对象.start()
进程相关指令
1. 查看当前进程对象 : multiprocessing.current_process()
2. 获取当前进程id : os.getpid()
3. 获取父进程 : os.getppid()
4. 杀死进程 : os.kill(进程id, 9)
5. linux下获取进程id : ps aux
进程传参
1. args : 位置参数,元组形式 multiprocessing.Process(target=函数名,args=())
2. kwargs : 关键字参数, 字典方式 multiprocessing.Process(target=函数名,kwargs={ })
进程的注意点
1. 进程之间不共享全局变量: 创建一个进程,就是对主进程资源的一份拷贝,每个进程只能修改自己进程中的全局变量,不会影响其他进程
2. 主进程会等待所有子进程执行结束再结束
让子进程随主进程结束而结束方法:
a. 手动销毁子进程 : sub_process.terminate()
b. 设置为守护主进程 ,设置在start之前 : sub_process.daemon = True
多线程
概念
1. 作用 : 线程是实现多任务的一种方式
2. 线程是CPU调度的基本单位
3. 每个进程默认有一个线程
创建线程
1. 导包 : import threading
2. 创建线程对象 : sub_thread = threading.Thread(target=func)
3. 启动线程 : sub_thread.start()
线程传参
1. args : 元组方式
2. kwargs : 字典方式
注意点
1. 线程执行顺序为无序 : 线程的执行需要CPU的调度,谁获得CPU,谁就先执行
2. 主线程会等待子线程结束后再结束
让子线程随主线程的结束而结束
a. 在创建对象的时候,传入参数 :daemon= True
b. 在创建对象之后线程启动之前,调用setDaemon(True)方法
3.线程共享全局变量
共享全局变量,由于不确定何时丢失CPU资源,会导致数据错乱(资源竞争)问题
互斥锁
保证只有一个线程能够获得锁
创建互斥锁
1.创建锁 : mutex = threading.Lock()
2. 加锁 : mutex.acquire()
3. 解锁 : mutex.release()
死锁
某个线程拿到互斥锁,使用完之后没有释放互斥锁
避免: 适时释放互斥锁