进程
进程、线程的使用都是由操作系统来调度的,而不是由程序员来操控的。
进程的定义:
进程就是一个正在运行的程序,是一个具有一定独立功能的程序关于某个数据集合的一次运行活动。
进程和程序的区别:
1. 程序就是一堆死的东西,没有生命周期
2.进程是有生命周期的,等一个任务进行完毕之后,进程就不存在了
进程只是一个过程,而线程才是真正去做任务的
"" 进程中是要有线程的,如果没有线程是没有意义的,一个进程中是可以有多个线程的,一个进程中至少要有一个线程。""
进程和线程都是由操作系统来调度的,进程是操作系统的一个独立的单位。
补充:cpu工作机制(其实CPU的工作机制是来回切换做到的)
1. 当cpu遇到I/O操作时,会剥夺CPU的执行权限
2. 当遇到的任务需要占用大量的时间的时候,也会剥夺执行权限。
I/O密集型:(input、output)
遇到阻塞是,需要等待,但不会占用大量的CPU资源,比如:sleep
计算密集型:
没有遇到阻塞,但是需要占用大量的CPU资源,也不需要等待
操作系统的调度算法(了解,操作系统会自行选择哪一种算法)
1. 先来先服务调度算法
2,短作业优先调度算法
3. 时间片轮转法
4. 多级反馈队列
进程的并发和并行
并行:
在‘同一时刻’,同时执行任务。单核的CPU不能做到并行。
在同一时刻想要执行多个任务,必须要求CPU有多个处理器(核)
并行:
在一段时间内,看起来是同时执行任务 ,事实上,不是同一时刻。
同步异步阻塞非阻塞

同步异步
同步异步关注的是消息通信机制
同步依赖于上一次的结果
异步不依赖于上一次的结果
异步的效率比同步的效率高

阻塞与非阻塞
阻塞和非阻塞关注的是程序在等待调用结果(消息,返回值)是的状态。
阻塞:调用结果返回之前,当前线程会被挂起。只有得到结果之后才会返回
非阻塞:在不能立刻得到结果之前,该调用不会阻塞当前线程。

开启进程
使用的是内置模块:multiprocess
""在Windows系统中,开启进程必须写在__main__中,在其他系统中不用加""
from multiprocessing import Process def task(): print('helloworld') if __name__ == '__main__': # 先实例化得到一个进程对象p p = Process(target=task) # 开启进程 p.start()
Process类的参数
参数介绍:
group参数未使用,值始终为None
target表示调用对象,即子进程要执行的任务
args表示调用对象的的位置参数元组
kwargs表示调用对象的字典
name为子进程的名字
先执行主进程,在执行子进程
"""这个开启进程只是通知操作系统去开进程,因为开启进程需要时间的,所以,在一瞬间进程并没有开起来,然后代码往下执行了"""
from multiprocessing import Process def task(name,name1,age,gender): print('helloworld') print(name) # feifei print(name1) # jolly print('age:', age) # age: 4 print('gender:', gender) # gender: male if __name__ == '__main__': # 先实例化得到一个进程对象p,并进行传参 p = Process(target=task,name='hua',args=('feifei','jolly'),kwargs={'age':4,'gender':'male'}) # 开启进程 p.start()
print(p.name) # 打印进程的名字 hua
"""现在的现象是:主进程代码先执行,然后执行子进程里的代码,并且主进程代码执行完毕之后,子进程的代码并没有结束"""
结果:

daemon表示守护进程,作用:主进程结束,子进程也结束,要想使用守护进程,必须写在start之前。
from multiprocessing import Process
def task(name,name1,age,gender): print('helloworld') print(name) # feifei print(name1) # jolly print('age:', age) # age: 4 print('gender:', gender) # gender: male if __name__ == '__main__': # 先实例化得到一个进程对象p,并进行传参
# 开启的这个进程叫子进程
p = Process(target=task,name='hua',args=('feifei','jolly'),kwargs={'age':4,'gender':'male'}) # 守护进程:主进程结束后,子进程也结束 p.daemon = True # 守护进程 # 开启进程 p.start()
print(p.name) # 查看进程的名字 hua
结果如图所示:

方法介绍
from multiprocessing import Process def task(name,name1,age,gender): print('helloworld') print(name) # feifei print(name1) # jolly print('age:', age) # age: 4 print('gender:', gender) # gender: male if __name__ == '__main__': # 先实例化得到一个进程对象p,并进行传参 p = Process(target=task,name='hua',args=('feifei','jolly'),kwargs={'age':4,'gender':'male'}) # 守护进程:主进程结束后,子进程也结束 # p.daemon = True # 守护进程 # 开启进程 p.start() # 强制执行 p.terminate() # 查看p进程是否运行 print(p.is_alive()) # 此时返回True ,因为操作系执行需要一段时间 print(p.name) # 打印进程的名字 hua
p.terminate() : 强制结束子进程
p.is_alive() : 判断进程是否结束,返回结果为布尔值
from multiprocessing import Process def task(name,name1,age,gender): print('helloworld') print(name) # feifei print(name1) # jolly print('age:', age) # age: 4 print('gender:', gender) # gender: male if __name__ == '__main__': # 先实例化得到一个进程对象p,并进行传参 p = Process(target=task,name='hua',args=('feifei','jolly'),kwargs={'age':4,'gender':'male'}) # 守护进程:主进程结束后,子进程也结束 # p.daemon = True # 守护进程 # 开启进程 p.start() # 杀死进程 p.terminate() import time time.sleep(1) # 查看p进程是否运行 print(p.is_alive()) # 此时返回False print(p.name) # 打印进程的名字 hua
p.join() : 等子进程执行完毕,在执行主进程
from multiprocessing import Process def task(name,name1,age,gender): print('helloworld') print(name) # feifei print(name1) # jolly print('age:', age) # age: 4 print('gender:', gender) # gender: male if __name__ == '__main__': # 先实例化得到一个进程对象p,并进行传参 p = Process(target=task,name='hua',args=('feifei','jolly'),kwargs={'age':4,'gender':'male'}) # 开启进程 p.start() # 先执行子程序,再执行主程序 p.join() print(p.name) # 打印进程的名字 hua
结果:

开启多进程
利用for循环来完成多个字进程的运行
from multiprocessing import Process def task(i): print("task:", i) if __name__ == '__main__': for i in range(5): # 开启多进程之后,有可能是没有顺序的 p = Process(target=task, args=(i, )) p.start() print(123)
结果:

先执行所有的子程序在执行主程序
from multiprocessing import Process def task(i): print("task:", i) if __name__ == '__main__': ll = [] for i in range(5): # 开启多进程之后,有可能是没有顺序的 p = Process(target=task, args=(i, )) p.start() ll.append(p) # 将所得到的进程对象加在列表中 for j in ll: # for循环取值,取出一个个子进程对象 j.join() """想让所有的子进程先执行完,在执行主进程""" print(123)
进程锁
锁:加锁是为了保证数据的安全。
在MySQL中:行锁、表锁、悲观锁、乐观锁、等
在python中:进程锁、互斥锁、GIL锁、死锁等
def task(i,lock): # 上一把锁 lock.acquire() print("第%s个进程进来了" % i) print("第%s个进程走了" % i) # 释放锁 lock.release() from multiprocessing import Process from multiprocessing import Lock if __name__ == '__main__': # 实例化 lock = Lock() for i in range(5): # 开启多进程之后,有可能是没有顺序的 p = Process(target=task, args=(i,lock)) p.start() print(123)
结果:

进程间的通信(IPC机制)
进程是可以开启多个的,进程与进程之间是相互独立的,互不影响,进程是操作系统的一个独立单元。一个进程崩溃了,其他的进程不会受到影响。
n =100 def task(name,name1,age,gender): global n n = 1 from multiprocessing import Process if __name__ == '__main__': # 先实例化得到一个进程对象p p = Process(target=task)
结果:

从上面可以看出:
在一个进程中不能修改另外一个进程的数据,言外之意就是进程之间的数据是隔离的,互不影响。
要想在一个进程中使用另外一个进程中的数据,需要让进程之间通信,也就是IPC机制
