并发:
在一个时间点只能执行一个任务,在一段时间内执行多个任务。
并行:
在一个时间点同时执行多个任务
1. 进程
进程由操作系统控制,多核cpu可以同时执行多个进程。
1.1 使用
from multiprocessing import Process
p1 = Process(target = fun ,args=(2,))
p1.start()
args参数需要传一个元组
1.2 进程标识符
1.2.1 父进程
1.2.2 进程id
pid
os.getpid()返回当前进程id
os.getppid()返回父进程id
1.2.3 进程名
可以指定一个name属性,
p1.pid
进程p1的id
p1.ppid
进程p1的父进程id
p1.name
进程p1的名字
例子:
from multiprocessing import Process
import time
class MyProcess(Process):
def run(self):
time.sleep(1)
print('task has been done!')
if __name__ == '__main__':
t1 = MyProcess()
t1.start()
2.线程
又叫轻量进程,使用类似进程
from threading import Thread
多线程不可能并行,GIL全局解释性锁,限制线程在任何进程中同一时间点只能有一个线程在执行。
2.1 线程标识符
2.1.1 主线程
任何一个进程,默认会启动一个线程,这个线程就是主线程
2.1.2 线程id
current_thread() 可以返回当前线程的实例
main_thread()返回当前进程的主线程实例
ident属性获取线程实例的id,由解释器指定非零的整数
current_thread().name
current_thread().ident
main_thread().name
main_thread().ident
3.多进程与多线程的同步
3.1 守护模式daemon
3.1.1多进程守护
from multiprocessing import Process
import os, time
def task():
time.sleep(3)
print('当前进程为%s,父进程为%s' % (os.getpid(), os.getppid()))
if __name__ == '__main__':
p1 = Process(target=task, name='进程1')
p1.daemon = True
p1.start()
time.sleep(2)
主进程运行2秒结束,子进程守护未完成打印任务就结束了
3.1.2 多线程
from threading import Thread,current_thread
import time
def task1():
time.sleep(2)
print(current_thread().name,current_thread().ident)
def task2():
time.sleep(3)
print(current_thread().name, current_thread().ident)
if __name__ == '__main__':
t1 = Thread(target=task1,name='线程1',daemon=True)
t1.start()
# print(current_thread().name)
t2 = Thread(target=task2, name='线程2')
t2.start()
time.sleep(1)
print(current_thread().name,current_thread().ident)
主线程1秒运行结束,但线程2非守护,等待线程2 运行结束后,整个进程才算结束。在整个进程结束前,线程1已经完成打印任务。
3.2 等待
join()方法,可以让父进程(主线程)等待子进程(子线程)执行完毕之后,再往下执行。阻塞主进程(主线程)切换到 join方法所在的进程(线程),执行完毕再切换回join代码位置继续执行。