You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Python未绑定对象的影响及多线程中Queue对象重新赋值后的引用问题

关于Python线程与队列对象引用的问题解答

首先直接给你结论:每一对线程都会牢牢持有启动时传入的原始队列对象,完全不受后续myQueue变量重新赋值的影响,你想要的“每对线程共享唯一队列”的目标其实已经实现了。

核心原理:Python的变量与对象是分离的

在Python里,变量(比如myQueue)其实只是一个指向对象的“引用标签”,而非对象本身。当你执行myQueue = queue.Queue()时,是先创建一个新的Queue对象,再让myQueue这个标签指向它。

启动线程时,args=(myQueue,)是把当前myQueue指向的Queue对象的引用复制了一份传递给线程函数的参数。这时候就算你之后把myQueue指向新的Queue对象,旧的Queue对象依然存在——因为那两个线程的函数参数还在引用它,它不会变成“未绑定状态”。

针对你的场景逐一解答

  1. 旧Queue对象的变化:
    只要启动的线程还在运行,旧Queue对象就会被线程的参数引用着,不会被Python的垃圾回收机制回收。只有当这两个线程都结束运行、不再有任何引用指向这个旧Queue时,它才会被回收。

  2. 线程使用的队列是否会更新:
    绝对不会。每个线程在启动时就拿到了对应Queue对象的独立引用,之后无论外部的myQueue变量怎么变更,线程内部使用的都是一开始传入的那个队列实例。所以你的循环里,每一次迭代创建的一对线程,都会共享属于自己的唯一队列,和其他迭代的线程完全隔离。

验证小例子

你可以打印每个队列的唯一ID来确认,修改后的代码如下:

import queue, threading
def getFromQueue(myQueue):
    while True:
        item = myQueue.get()
        if item is None:  # 加停止信号避免线程无限循环
            break
        print(f"从队列ID {id(myQueue)} 获取到: {item}")

def putInQueue(myQueue, items):
    for item in items:
        myQueue.put(item)
    myQueue.put(None)  # 发送停止信号

msgList = [["消息组1-1", "消息组1-2"], ["消息组2-1", "消息组2-2"]]
for msg in msgList:
    myQueue = queue.Queue()
    print(f"为当前线程对创建了队列ID: {id(myQueue)}")
    threading.Thread(target=getFromQueue, args=(myQueue,)).start()
    threading.Thread(target=putInQueue, args=(myQueue, msg)).start()

运行后你会看到,每对线程打印的队列ID和循环中创建的队列ID完全一致,证明它们确实在使用各自的独立队列。

内容的提问来源于stack exchange,提问作者eng3

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.04.30 07:37:33