文章目录

  • 什么是线程与进程
  • 什么是进程
  • 什么是线程
  • Python 使用线程
  • 实验一
  • 顺序执行
  • 创建线程同时执行
  • 阻塞执行
  • 阻塞实现串行执行(join()方法)
  • 示例二:串行与并行累加
  • 顺序执行累加
  • 创建2个单线程分别执行累加
  • 多线程阻塞执行
  • 三个小实验数据对比
  • 结论:


什么是线程与进程

什么是进程

进程是操作系统运行程序的一个最基本的单位,是一个程序运行的实例,也是资源分配的基本单位,一个进程关联了操作系统的资源,包括地址空间,内存,I/O,CPU等等资源,进程与进程之间是相互独立不可互访的,保持了一定的独立性,在同级别下运行进程,进程之间的资源是相互抢夺的,操作系统会进程资源进行调度。如果需要实现进程间通信,可以通过管道,文件或者socket等等进行进程间通信。

什么是线程

线程是一堆可执行程序的上下文,一个进程至少包含一个线程,而一个进程通常有多个任务需要处理,此时可通过不同的线程执行不同的任务,线程是进程执行运算的最小单位。一个进程内的所有线程都共享这个进程的所有资源。

Python 使用线程

创建线程,需要用到创建线程的模块,简单的做个小测试,执行两个函数,写上两个任务,比较执行线程与不执行线程的耗时区别:

实验一

顺序执行

import time
import threading

def firstfunction(n):
    print("firstfunction:",n)
    time.sleep(1)

def secondaryfunction(m):
    print("secondaryfunction:",m)
    time.sleep(2)


start = time.time()
print("run in the main.....")
firstfunction(1)
secondaryfunction(2)
end = time.time()
print("use time:",end-start)

"""
run in the main.....
firstfunction: 1
secondaryfunction: 2
use time: 3.0252649784088135

Process finished with exit code 0
"""

创建线程同时执行

import time
import threading

def firstfunction(n):
    print("firstfunction:",n)
    time.sleep(1)

def secondaryfunction(m):
    print("secondaryfunction:",m)
    time.sleep(2)


start = time.time()
print("run in the main.....")
threading.Thread(target=firstfunction,args=(1,)).start()
threading.Thread(target=secondaryfunction,args=(2,)).start()

end = time.time()

print("use time:",end-start)

"""
run in the main.....
firstfunction: 1
secondaryfunction: 2
use time: 0.0

Process finished with exit code 0
"""

以上两个实验,其实是一个主进程在执行,内部包含两个线程。

阻塞执行

import time
import threading

def firstfunction(n):
    print("firstfunction:",n)
    time.sleep(3)
    print(time.time())

def secondaryfunction(m):
    print("secondaryfunction:",m)
    time.sleep(5)
    print(time.time())


start = time.time()
print("run in the main.....")
thread1 = threading.Thread(target=firstfunction,args=(1,))
thread2 = threading.Thread(target=secondaryfunction,args=(2,))

thread1.start()
thread2.start()

thread1.join()
thread2.join()

end = time.time()
print("use time:",end-start)

"""
run in the main.....
firstfunction: 1
secondaryfunction: 2
1610522242.126154
1610522244.1256802
use time: 5.000953912734985

Process finished with exit code 0
"""

阻塞实现串行执行(join()方法)

import time
import threading

def firstfunction(n):
    print("firstfunction:",n)
    time.sleep(3)
    print(time.time())

def secondaryfunction(m):
    print("secondaryfunction:",m)
    time.sleep(5)
    print(time.time())


start = time.time()
print("run in the main.....")
thread1 = threading.Thread(target=firstfunction,args=(1,))
thread2 = threading.Thread(target=secondaryfunction,args=(2,))

thread1.start()
thread1.join()


thread2.start()
thread2.join()

end = time.time()
print("use time:",end-start)

"""
run in the main.....
firstfunction: 1
1610522484.7876196
secondaryfunction: 2
1610522489.788924
use time: 8.002496004104614

Process finished with exit code 0
"""

示例二:串行与并行累加

顺序执行累加

import time


def add(n):
    start = time.time()
    sum = 0
    for i in range(n):
        sum +=i
    print(sum)
    end = time.time()
    print("consumer time is :",end - start)

begin = time.time()
add(100000000)
add(200000000)
end = time.time()
print("main consumer time is :",end - begin)


"""
4999999950000000
consumer time is : 7.672001361846924
19999999900000000
consumer time is : 16.13348913192749
main consumer time is : 23.805490493774414

Process finished with exit code 0

"""

耗时:23.805490493774414
函数1耗时:7.672001361846924
函数2耗时:16.13348913192749

创建2个单线程分别执行累加

import time
import threading

def add(n):
    start = time.time()
    sum = 0
    for i in range(n):
        sum +=i
    print(sum)
    end = time.time()
    print("consumer time is :",end - start)



begin = time.time()

thread1 = threading.Thread(target=add,args=(100000000,))
thread1.start()
thread2 = threading.Thread(target=add,args=(200000000,))
thread2.start()
end = time.time()
print("main consumer time is :",end - begin)


"""
main consumer time is : 0.0358586311340332
4999999950000000
consumer time is : 14.394654512405396
19999999900000000
consumer time is : 21.326332569122314

Process finished with exit code 0

"""

主线程耗时:0.0358586311340332
线程1耗时:14.394654512405396
线程2耗时:21.326332569122314

多线程阻塞执行

import time
import threading

def add(n):
    start = time.time()
    sum = 0
    for i in range(n):
        sum +=i
    print(sum)
    end = time.time()
    print("consumer time is :",end - start)



begin = time.time()

thread1 = threading.Thread(target=add,args=(100000000,))
thread1.start()
thread1.join()
thread2 = threading.Thread(target=add,args=(200000000,))
thread2.start()
thread2.join()
end = time.time()
print("main consumer time is :",end - begin)


"""
4999999950000000
consumer time is : 7.0818071365356445
19999999900000000
consumer time is : 15.460984468460083
main consumer time is : 22.542791604995728

Process finished with exit code 0

"""

主线程耗时:22.542791604995728
线程1耗时:7.0818071365356445
线程2耗时:15.460984468460083

三个小实验数据对比

实验

顺序执行

多线程并发执行

多线程阻塞执行

主线程

23.805490493774414

0.0358586311340332

22.542791604995728

线程1

7.672001361846924

14.394654512405396

7.0818071365356445

线程2

16.13348913192749

21.326332569122314

15.460984468460083

结论:

  1. 顺序执行与多线程阻塞执行耗时一样,多纯种阻塞就是顺序执行
  2. 多线程并发执行这个程序比顺序执行的速度还慢,且时间超过了顺序执行的时间。

对于这种一直累加是需要大量的CPU来进行计算的,所以线程并发并不适合多线程,多线程是需要线程间切换来使用CPU的计算时间的,而这种频繁的切换并不适合CPU密集型的业务,所以在此小实验中,大量计算是CPU密集型,所以串行比并行效率更高。所以在Python中,如果是I/O密码型的应用,可以使用多线程,如果是CPU密集型的,请用其它语言