【一】threading模块开启线程的两种方式
【1】直接调用Thread
from threading import Thread
import time
def task(name):
print(f'{name} is starting')
time.sleep(3)
print(f'{name} is ending')
def main():
t = Thread(target=task, args=("drake",))
# 创建线程的开销非常小,几乎代码运行的一瞬间线程就已经创建了
t.start()
if __name__ == '__main__':
main()
# drake is starting
# drake is ending
【2】继承Thread父类
from threading import Thread
import time
class MyThread(Thread):
def __init__(self, name):
super().__init__()
self.name = name
def run(self):
print(f'{self.name} is starting')
time.sleep(3)
print(f'{self.name} is ending')
def main():
t1 = MyThread('dream')
t2 = MyThread('uzi')
t1.start()
t2.start()
if __name__ == '__main__':
main()
# dream is starting
# uzi is starting
# uzi is ending
# dream is ending
【三】一个进程下开启多个线程和多个子进程的区别
【1】谁的开启速度快
from threading import Thread
from multiprocessing import Process
import time
def work():
print('hello')
def timer(func):
def inner(*args, **kwargs):
start_time = time.time()
res = func(*args, **kwargs)
print(f'函数 {func.__name__} 运行时间为:{time.time() - start_time}')
return res
return inner
@timer
def work_process():
# 在主进程下开启子进程
t = Process(target=work)
t.start()
@timer
def work_thread():
# 在主进程下开启线程
t = Thread(target=work)
t.start()
if __name__ == '__main__':
work_thread()
work_process()
# hello
# 函数 work_thread 运行时间为:0.0009613037109375
# 函数 work_process 运行时间为:0.03390765190124512
# hello
【2】查看pid
from threading import Thread
from multiprocessing import Process
import os
def work():
print(f"该程序pid:{os.getpid()}")
def work_thread():
# 在主进程下开启多个线程,每个线程都跟主进程的pid一样
t1 = Thread(target=work)
t2 = Thread(target=work)
t1.start()
t2.start()
def work_process():
# 开多个进程,每个进程都有不同的pid
p1 = Process(target=work)
p2 = Process(target=work)
p1.start()
p2.start()
if __name__ == '__main__':
work_thread()
# 该程序pid:100620
# 该程序pid:100620
work_process()
# 该程序pid:100772
# 该程序pid:103280
【3】同一进程内的线程共享该进程的数据
from threading import Thread
from multiprocessing import Process
def work():
global num
num = 0
def work_process():
num = 100
p = Process(target=work)
p.start()
p.join()
print(f'进程num:{num}') # 子进程p已经将自己的全局的n改成了0,但改的仅仅是它自己的,查看父进程的n仍然为100
# 进程num:100
def work_thread():
num = 1
t = Thread(target=work)
t.start()
t.join()
print(f'线程num:{num}') # 查看结果为1,因为同一进程内的线程之间共享进程内的数据
# 线程num:1
if __name__ == '__main__':
# 多进程:子进程只改自己的
work_process()
# 多线程:数据发生错乱,同一进程内的线程之间共享数据
work_thread()
【四】多线程并发的服务端
- 服务端
from threading import Thread
from socket import *
# 不写参数:默认是TCP协议
# 创建服务器对象
server = socket()
# 绑定 IP PORT
IP = '127.0.0.2'
PORT = 8081
ADDR = (IP, PORT)
server.bind(ADDR)
# 监听
server.listen(5)
# 将接受处理数据部分封装成函数调用
def run(conn):
while True:
from_client = conn.recv(1024)
# 接受的信息为空时,会无限循环
if len(from_client) == 0:
break
# 接收到客户端的信息
print(f"这是来自客户端的消息:{from_client.decode()}")
# 返回给客户端信息
to_client = '你的消息我已收到!'
conn.send(to_client.encode())
# 关闭链接
conn.close()
def main():
while True:
# 接受连接对象和 ip port
conn, addr = server.accept()
t = Thread(target=run, args=(conn,))
t.start()
if __name__ == '__main__':
main()
- 客户端
from socket import *
# 不写参数:默认是TCP协议
# 创建客户端对象
client = socket()
# 绑定 IP PORT
IP = '127.0.0.2'
PORT = 8081
ADDR = (IP, PORT)
client.connect(ADDR)
while True:
# 向服务端发数据
message = input("请输入发送给服务端的消息:").strip()
client.send(message.encode())
# 接受服务器返回的数据
data_from_server = client.recv(1024)
print(data_from_server.decode())
【五】线程对象的属性和方法
【1】线程对象的 join 方法
from threading import Thread
import time
def task(name):
print(f'{name} is starting')
time.sleep(3)
print(f'{name} is ending')
def main():
t1 = Thread(target=task, args=('drake',))
t2 = Thread(target=task, args=('uzi',))
t1.start()
t2.start()
# 主线程等待子进程结束之后再运行
t1.join()
t2.join()
if __name__ == '__main__':
main()
# drake is starting
# uzi is starting
# drake is ending
# uzi is ending
【2】获取当前进程的名字——current_thread
from threading import Thread, active_count, current_thread
import time
def task():
# 获取当前线程的名字
print(f'该线程的名字:{current_thread().name}')
time.sleep(2)
def main():
t1 = Thread(target=task)
t2 = Thread(target=task)
t1.start()
t2.start()
print(f'该线程的名字:{current_thread().name}')
if __name__ == '__main__':
main()
# 该线程的名字:Thread - 1(task)
# 该线程的名字:Thread - 2(task)
# 该线程的名字:MainThread
【3】统计当前活跃的线程数——active_count
from threading import Thread, active_count, current_thread
import time
def task():
# 获取当前线程的名字
print(f'该线程的名字:{current_thread().name}')
time.sleep(2)
def main():
t1 = Thread(target=task)
t2 = Thread(target=task)
t1.start()
t2.start()
# 统计当前活跃的线程数
print(f'当前活跃的线程数:{active_count()}')
print(f'该线程的名字:{current_thread().name}')
if __name__ == '__main__':
main()
# 该线程的名字:Thread - 1(task)
# 该线程的名字:Thread - 2(task)
# 当前活跃的线程数:3
# 该线程的名字:MainThread
标签:__,name,Thread,work,线程,操作,多线程,def
From: https://www.cnblogs.com/ligo6/p/18218353