Skip to main content
 首页 » 编程设计

Python多线程基础混淆

2025年05月04日21jirigala

我有以下代码:

import time 
from threading import Thread 
 
def fun1(): 
 time.sleep(5) 
 
def fun2(): 
 time.sleep(5) 
 
def fun3(): 
 time.sleep(5) 
 
def fun4(): 
 time.sleep(5) 
 
if __name__ == '__main__': 
  t1 = Thread(target=fun1, args=()) 
  t2 = Thread(target=fun2, args=()) 
  t3 = Thread(target=fun3, args=()) 
  t4 = Thread(target=fun4, args=()) 
  t1.start() 
  t2.start()  
  t3.start()  
  t4.start() 
  start = time.clock() 
  t1.join() 
  t2.join() 
  t3.join() 
  t4.join() 
  end = time.clock() 
  print("Time Taken = ",end-start) 

Que1:一次只有一个线程会被服务,这意味着如果控件是线程 t1,其余线程将等待。一旦线程 t2 发生上下文切换,其余所有线程(t1、t3 和 t4)将等待。 这样理解对吗?

Que2:如果我对 Que1 的理解是正确的,总时间(开始 - 结束)应该是 20 秒(与以顺序方式而不是线程方式运行一样好)......但它有点接近 5 秒。 ...为什么?在一天结束时,线程将按顺序(尽管不是全部)一个接一个地执行 请通俗地解释一下,我的理解哪里不对?

问题 3:如果我使用多处理做同样的事情怎么办?执行会有什么不同?

Que4:假设(假设)fun1() 的代码对路由器 1 执行 1000 次重复计数 ping,耗时 1 分钟。 类似地,fun2() 对路由器 2 执行 1000 次重复计数 ping,耗时 1 分钟。 类似地,fun3() 对路由器 3 执行 1000 次重复计数 ping,耗时 1 分钟。

如果我按顺序执行此操作,总预期时间为 3 分钟(ping 到 R1,然后 ping 到 R2,然后 ping 到 R3) 但是当我使用线程执行此操作时,总执行时间几乎接近 1 分钟。为什么 ?我无法理解。

请您参考如下方法:

Python 中的阻塞调用(sleep,等待 I/O 或锁)释放 GIL,允许其他线程在被阻塞时运行,因此所有四个线程都可以 sleep 并行,这就是为什么您会看到五秒钟的延迟。如果你想看到 GIL 争用的影响,让线程函数做一些 CPU 绑定(bind)的事情,例如

def fun(): 
    for _ in xrange(1000000000): 
        pass 

multiprocessing 不会改变 sleep 情况,因为您不受 GIL 限制,但它会改善 CPU 限制情况的挂钟时间如果您有多个内核可以运行。