abababab 发表于 2023-5-4 14:20:34

Thread 线程锁后,返回值问题?

from threading import Thread
from threading import Lock
import time

n = 100                           #共100张票
def task():
    global n                     
    mutex.acquire()               #上锁
    # temp = n                        #赋值给临时变量
    # time.sleep(0.1)               #休眠0.1秒
    # n = temp - 1                  #数量减1
    time.sleep(0.1)               #休眠0.1秒
    n = n-1
    print("购买成功,剩余%d张电影票"%n)
    mutex.release()               #释放锁
    return ("购买成功,剩余%d张电影票"%n)

if __name__ == "__main__":
    mutex = Lock()                  #实例化LOCK类
    t_list = []                     #初始化一个列表
    for i in range(10):
      t = Thread(target=task)   #实例化线程类
      t_list.append(t)            #将线程实例存入列表中
      t.start()                   #创建线程
   
    for t in t_list:
      t.join()                  #等待子线程结束
    data = t.join()
    print("data ",data )


怎么在主函数取回task的返回值?data取回 none

isdkz 发表于 2023-5-4 14:22:52

在您的代码中,您尝试通过调用 t.join() 来获取 task() 函数的返回值。然而, Thread 对象的 join() 方法并不返回调用线程的返回值。为了解决这个问题,您可以使用 concurrent.futures 库中的 ThreadPoolExecutor ,它允许您轻松地获取线程返回值。请看下面的示例:

from concurrent.futures import ThreadPoolExecutor
import time
from threading import Lock

n = 100                           # 共100张票
mutex = Lock()                      # 实例化LOCK类


def task():
    global n
    global mutex
    with mutex:                     # 上锁
      time.sleep(0.1)             # 休眠0.1秒
      n = n - 1                   # 数量减1
      result = "购买成功,剩余%d张电影票" % n
    return result                   # 释放锁


if __name__ == "__main__":
    with ThreadPoolExecutor(max_workers=10) as executor:
      # 提交任务并获取返回值
      results = list(executor.map(task, * 10))

    for result in results:
      print(result)

    print("data ", results[-1])


在这个示例中,我们使用了 ThreadPoolExecutor 来创建和执行线程。通过将 task 函数映射到 * 10 列表,我们创建了10个线程,每个线程都执行一次 task 函数。 executor.map() 方法会返回一个结果列表,其中包含 task 函数的返回值。最后,我们可以从结果列表中获取我们需要的返回值。

abababab 发表于 2023-5-4 14:47:30

isdkz 发表于 2023-5-4 14:22
在您的代码中,您尝试通过调用 t.join() 来获取 task() 函数的返回值。然而, Thread 对象的 join() 方法并 ...

TypeError: task() takes 0 positional arguments but 1 was given

* 10 是啥意思?

isdkz 发表于 2023-5-4 14:50:40

abababab 发表于 2023-5-4 14:47
TypeError: task() takes 0 positional arguments but 1 was given

* 10 是啥意思?

这里的 * 10是创建一个包含 10 个None元素的列表。当我们使用executor.map()函数时,它需要将传递给task()函数的参数作为第二个参数。由于我们的task()函数没有接收任何参数,所以这里产生了错误。

为了修复这个问题,您可以将task()函数修改为接受一个参数(即使我们实际上不使用它)。下面是修改后的代码:

from concurrent.futures import ThreadPoolExecutor
import time
from threading import Lock

n = 100                           # 共100张票
mutex = Lock()                      # 实例化LOCK类


def task(dummy):                  # 修改这里,添加一个参数
    global n
    global mutex
    with mutex:                     # 上锁
      time.sleep(0.1)             # 休眠0.1秒
      n = n - 1                   # 数量减1
      result = "购买成功,剩余%d张电影票" % n
    return result                   # 释放锁


if __name__ == "__main__":
    with ThreadPoolExecutor(max_workers=10) as executor:
      # 提交任务并获取返回值
      results = list(executor.map(task, * 10))

    for result in results:
      print(result)

    print("data ", results[-1])


现在, task()函数接受一个名为dummy的参数,但我们在函数内部并未使用它。这样, executor.map()可以正常工作,因为它会将列表 * 10中的每个None元素作为参数传递给task()函数。
页: [1]
查看完整版本: Thread 线程锁后,返回值问题?