自学Python 51 多线程开发(一)threading模块

艽野尘梦520 2022-08-06 08:00:05 阅读数:56

Python开发多线程线程自学

Python​ threading模块

活动地址:CSDN21天学习挑战赛



当一个程序在同一时间只能做一件事情时就是单线程程序,这样的程序的功能会显得过于简单,肯定无法满足现实的需求前面学习的程序大多数都是单线程程序,那么究竟什么是多线程呢?能够同时处理多个任务的程序就是多线程程序,多线程程序的功能更加强大,能够满足现实生活中需求多变的情况。Python作为一门面向对象的语言,支持多线程开发功能。在本章中将详细讲解Python多线程开发的基本知识。


一、线程和进程介绍

在计算机应用中,线程是程序运行的基本执行单元,当操作系统(不包括单线程的操作系统,如微软早期的 DOS)在执行一个程序时,会在系统中建立一个进程,而在这个进程中,必须至少建立一个线程(这个线程被称为主线程)作为这个程序运行的入口点。因此,在操
作系统中运行的任何程序都至少有一个主线程。
进程和线程是现代操作系统中两个必个可少的运行模型。在操作系统中可以有多个进程,这些进程包括系统进程(由操作系统内部建立的进程)和用户进程(由用户程序建立的进程;在一个进程中可以有一个或多个线程。进程和进程之间不会共享内存,也就是说,系统中的进程是在各自独立的内存空间中运行的。而一个进程中的线程可以共享系统分派给这个进程的内存空间。
线程不仅可以共享进程的内存,而且还拥有一个属于自己的内存空间,这段内存空间也叫作线程栈,是在建立线程时由系统分配的,主要用来保存线程内部所使用的数据,如线程执行函数中所定义的变量。在操作系统将进程分成多个线程后,这些线程可以在操作系统的管理下并发执行,从而极大地提高了程序的运行效率。虽然线程的执行从宏观上看是多个线程同时执行,但是实际上这只是操作系统的障眼法。由于一块CPU同时只能执行一条指令,因此,在拥有一块 CPU的计算机上不可能同时执行两个任务。而操作系统为了能提高程序的运行效率,在一个线程空闲时会撤下这个线程,并且会让其他的线程习来执行,这种方式叫作线程调度。

二、使用 threading模块

在Python程序中,可以通过“_thread”和“threading(推荐使用)”这两个模块来处理线程。在 Python3程序中,thread模块已被废弃,Python 官方建议使用threading模块代替。所以,在Python3中不能再使用thread模块,但是为了兼容Python3以前的程序,在 Python3中将thread模块重命名为“_thread"。
在Python 3程序中,可以通过两个标准库(_thread和 threading)提供对线程的支持。其中“_thread”提供了低级别的、原始的线程以及一个简单的锁,它相比于 threading模块的功能还是比较有限的。在本节的内容中,将详细讲解使用 threading模块的核心知识。

2.1 threading模块的核心方法

在 threading模块中,除了包含“ _thread”模块中的所有方法外,还提供了其他核心方法,如下表所示。

核心方法描述
threading.currentThread()返回当前的Thread对象,这是一个线程变量。如果调用者控制的线程不是通过threading模块创建的,则返回一个只有有限功能的虚假线程对象
threading.enumerate()返回一个包含正在运行的线程的list。正在运行指线程启动后、结束前,不包括启动前和终止后的线程
threading.activeCount()返回正在运行的线程数量,与len(threading.enumerate())有相同的结果
threading.main_thread()返回主Thread对象。在正常情况下,主线程是从Python解释器中启动的线程
threading.settrace(func)为所有从 threading模块启动的线程设置一个跟踪方法。在每个线程的run方法调用之前,func将传递给sys.settrace()
threading.setprofile(func)为所有从 threading模块启动的线程设置一个 profile()方法。这个 profile()方法将在每个线程的run()方法被调用之前传递给sys.setprofile()

在 threading模块中,还提供了常量 threading.TIMEOUT_MAX,这个 timeout参数表示阻塞方法(Lock.acquire()、RLock.acquire()和 Condition.wait(),等)允许等待的最长时限,设置超过此值的超时将会引发OverflowError错误。

2.2 使用 Thread对象

除了前面介绍的核心方法外,在模块 threading中还提供了类 Thread来外理线程。Thread是 threading模块中最重要的类之一,可以使用它来创建线程:一种是通过继承Thread类,重写它的run方法;另一种是创建一个threading.Thread对象,它的初始化函数( _ init_ )中将可调用对象作为参数传入。类Thed的讲法格式如下所示:

classthreading.Thread(group=None, LargeteNone,name=None, args=(), kwargs={ }, *,daemon=None)

上述参数的具体说明如下表所示。

参数名称描述
group应该为None, 用于在实现ThreadGroup类时的未来扩展
target是将被run()方法调用的可调用对象。默认为None, 表示不调用任何东西
name是线程的名字。在默认情况下,以"Thread-N" 的形式构造一个唯一的名字, N是一个小的十进制整数
args是给调用目标的参数元组,默认为0
kwargs是给调用目标的关键字参数的一个字典,默认为“{}”
daemon如果其值不是None,则守护程序显式设置线程是否为daemonic.如果值为None(默认值),则属性dacmonic从当前线程继承

在Python程序中,如果了类覆盖Thread构造函数,则必须保证在对线程做任何事之前调用基类的构造函数(Thread._ init_())。例如在下面的实例中,演示了直接在线程中运行函数的过程。

import threading
def zhiyun(x,y): #定义函教zhiyun()
for i in range(x,y): #遍历操作
print(str(i*i)+';') #打印输出一个数的平方
ta = threading.Thread(target=zhiyun,args=(1,6))
tb = threading.Thread(target=zhiyun,args=(16,21))
print('数字的平方计算')
print('数字的平方计算是:')
ta.start() #启动第1个线程活动
tb.start() #启动第2个线程活动

在上述实例代码中,首先定义函数zhiyun(),然后以线程方式来运行这个函数,并且在每次运行时传递不同的参数。运行后两个子线程会并行执行,可以分别计算出一个数的平方并输出,这两个子线程是交替运行的。

版权声明:本文为[艽野尘梦520]所创,转载请带上原文链接,感谢。 https://blog.csdn.net/weixin_46066007/article/details/126182040