一般程序提速的方法有:单线程串行,多线程并发,多进程并行,多机器并行。
我主要学习了多进程和多线程,其实关于两者的具体分别我也不是很清楚,只是知道,线程是CPU和IO同时执行,进程是多核CPU实现的。
实现多进程或者线程的大概步骤是:
1:导入模块
2:创建进程/线程对象
3:启动进程/线程对象
4:(额外的)可以获取进程/线程的编号
实现代码操作:
import multiprocessing#导入多进程模块
import time
def sing():
for i in range(3):
print('---唱歌-----')
time.sleep(1)
def dance():
for i in range(3):
print('---跳舞---')
time.sleep(1)
if __name__ == "__main__":
run_code = 0
'未使用多进程'
start1=time.time()
dance()
sing()
over1=time.time()
time=(over1-start1)*100
print(time)
#花费时间是605
'使用多进程'
# target是指的函数名,args和kwargs是负责传参的,不过一个是元组方式,一个是字典形式
# 创建进程对象
start = time.time()
dance_process=multiprocessing.Process(target=dance)
sing_process=multiprocessing.Process(target=sing)
#启动进程对象
dance_process.start()
sing_process.start()
print('-----')
over=time.time()
print('---',(over-start)*100)#1.65
可以知道,使用多进程确实可以提高处理任务的速度。
还有一个我认为重要的知识点就是:主进程守护,其原理类似于:我们打开浏览器,在浏览器里面打开许多个子浏览器,当我们关闭主浏览器窗口时,许多子浏览器页面也会关闭,并不会继续执行。
下面这个代码是没有添加主进程守护,导致主进程结束了,子进程还在运行,这样与我们设想的不一样。
import multiprocessing#导入多进程模块
import time
def sing():
for i in range(10):
print('---子进程正在运行-----')
time.sleep(1)#睡眠1秒运行一次
if __name__ == "__main__":
run_code = 0
sing_a=multiprocessing.Process(target=sing)
sing_a.start()
time.sleep(1)#运行1秒休息一次
print('主进程结束')
我们尝试添加主进程守护:结构类似是 进程对象.daemon=True
import multiprocessing#导入多进程模块
import time
def sing():
for i in range(10):
print('---子进程正在运行-----')
time.sleep(0.5)#睡眠0.5秒运行一次
if __name__ == "__main__":
run_code = 0
sing_a=multiprocessing.Process(target=sing)
sing_a.daemon=True
sing_a.start()
time.sleep(2)#运行2秒休息一次
print('主进程结束')
这样就会出现我们想要的结构:
这样就能达到我们想要的功能:即主进程关闭,子进程不在运行。
下面我们再来看看:
如何知道自己的主进程子进程编号:(进程之间是并发的,无序的)
import os
import threading#导入多线程模块
import multiprocessing#导入多进程模块
import time
#print(threading.active_count())
#print(threading.enumerate())
#print(threading.current_thread())
def sing():
for i in range(3):
print('---唱歌-----')
print('子进程1编号:',os.getpid())
print('主进程的编号:',os.getppid())
time.sleep(1)
def dance():
for i in range(3):
print('---跳舞---')
print('子进程2编号:', os.getpid())
print('主进程的编号:', os.getppid())
time.sleep(1)
if __name__ == "__main__":
run_code = 0
'未使用多进程'
# start1=time.time()
# dance()
# sing()
# over1=time.time()
# time=(over1-start1)*100
# print(time)#花费时间是605
'使用多进程'
# target是指的函数名,args和kwargs是负责传参的,不过一个是元组方式,一个是字典形式
# 创建进程对象
start = time.time()
dance_process=multiprocessing.Process(target=dance)
sing_process=multiprocessing.Process(target=sing)
#启动进程对象
dance_process.start()
sing_process.start()
print('-----')
over=time.time()
print('---',(over-start)*100)#1.65
得到的结果如下:
还有关于创建进程对象中,关于属性的问题,解释如下:
target是指的函数名,args和kwargs是负责传参的,不过一个是元组方式,一个是字典形式
至此,多进程就大概讲完了,多线程和多进程大概模板一样,只不过调用的模块不一样,
例如:导入模块 import threading
创建线程对象:???=threading.Thread(target=?,args=?,daemon=True)
只不过关于守护主线程,将代码daemon=True,放进了创建线程对象的属性中去了,大家可以自己去练习。