进程和线程
进程和线程的原理
线程是操作系统能够进行运算调度的最小单位。它被包含在进程之中,是进程中的实际运作单位。一条线程指的是进程中一个单一顺序的控制流,一个进程中可以并发多个线程,每条线程并行执行不同的任务。
程序并不能单独运行,只有将程序装载到内存中,系统为它分配资源才能运行,而这种执行的程序就称之为进程。程序和进程的区别就在于:程序是指令的集合,它是进程运行的静态描述文本;进程是程序的一次执行活动,属于动态概念
总而言之:
1、进程是一堆资源的集合,线程是一串指令的集合,进程无法直接参与运算,而线程才是控制指令运算的主体。进程中至少包含一个线程,可以通过主线程来创建子线程,但子线程和主线程没有所属关系,不会因为关闭了主线程而导致其他子线程一起关闭。同事主线程和子线程对资源空间是共享的,也就是说修改了一个线程的可能会影响到其他的线程对数据的访问结果。
2、一个主进程可以创建多个子进程,创建的子进程相当于对主进程的克隆,进程与进程之间的数据是独立的,如果他们之间要互相访问的话,就需要中间的代理。如果关闭了主进程的话,子进程要一同被关闭。但如果只是修改了一个进程的数据,那么对于其他进程的数据不存在影响,因为进程和进程之间的数据是不可共享的。
3、多线程运行其实同一时间只有一个线程在运行,是由于CPU具有对上下文快速切换作用,而且切换的时间很短,感官上看似同一时间运行不同任务,所以基于CPU对上下文的这种特性利用多线程处理任务比较快。
进程和线程的区别
1、线程共享内存空间,进程的内存是独立的
2、同一个进程的线程之间可以直接交流,两个进程想通信,必须通过一个中间代理来实现
3、创建新线程很简单, 创建新进程需要对其父进程进行一次克隆
4、一个线程可以控制和操作同一进程里的其他线程,但是进程只能操作子进程
线程实例:
#!/usr/bin/env python
# -*- coding:utf-8 -*-
import time
import threading
def addNum():
global num #在每个线程中都获取这个全局变量
print('--get num:',num )
time.sleep(1)
lock.acquire() #修改数据前加锁
num -=1 #对此公共变量进行-1操作
lock.release() #修改后释放
num = 100 #设定一个共享变量
thread_list = []
lock = threading.Lock() #生成全局锁
for i in range(100):
t = threading.Thread(target=addNum)
t.start()
thread_list.append(t)
for t in thread_list: #等待所有线程执行完毕
t.join()
print('final num:', num )
实例说明:
程序运行的结果为num为0:('final num:', 0)
代码里的线程方法join()表示主线程(程序本身)等待所有线程执行完毕后再往下执行直到结束。
又因为线程可以对共享数据同时修改,那么为了避免操作错误,应该在共享数据在修改前加上全局锁(lock()),这样在保证在一个线程在修改数据的时候其他线程不可修改,只有等其他线程对此数据不再访问了,另一个线程才可做修改操作。
进程实例:
什么时候用多线程,什么时候用多进程呢?
在python中,无论是单核还是多核CPU,python多线程只调用一个cpu,如果想让python能够同时调用多个CPU的话,那么就用到多进程了。
由于io操作不占用cpu,计算操作占用CPU,而多线程是一堆指令的集合,是用于操作CPU调度的,那么就用到计算操作,这时候就不适合cpu密集操作型的任务,适合io操作密集型的任务。
同理,多进程可以调度多核cpu运算,那么在密集cpu操作时比较适合多进程操作,而不适合IO密集型操作。
#!/usr/bin/env python
# -*- coding:utf-8 -*-
from multiprocessing import Process,Queue#这是进程Queue
import Queue #这是线程queue
import os
def info(title):
print(title)
print('module name:', __name__)
print('parent process:', os.getppid())
print('process id:', os.getpid())
print("\n\n")
def f(name):
info('\033[31;1mcalled from child process function f\033[0m')
print('hello', name)
if __name__ == '__main__':
info('\033[32;1mmain process line\033[0m')
p = Process(target=f, args=('bob',))#这里是启动一个子进程,如果启动多各子进程话,可以用for循环一次启动多个
p.start()
p.join()#使用join表示在子进程全部执行完毕后,主进程方可结束。
浙公网安备 33010602011771号