执行器映射未运行函数

问题描述 投票:0回答:1

我正在尝试复制比赛条件。下面的代码与使用Submit而不是map可以正常工作,但是我想了解为什么map不运行update方法。

import concurrent.futures
import time


class BankAccount:
    def __init__(self):
        self.balance = 100  # shared data

    def update(self, transaction, amount):
        print(f'{transaction} started')
        tmp_amount = self.balance  # reading from db
        tmp_amount += amount
        time.sleep(1)
        self.balance = tmp_amount
        print(f'{transaction} ended')


if __name__ == '__main__':
    acc = BankAccount()
    print(f'Main started. acc.Balance={acc.balance}')

    with concurrent.futures.ThreadPoolExecutor(max_workers=2) as ex:
        ex.map(acc.update, [dict(transaction='refill', amount=100),
                            dict(transaction='withdraw', amount=-200)])

    print(f'End of Main. Balance={acc.balance}')
python threadpoolexecutor
1个回答
2
投票

将各种参数传递到单独的可迭代中。

ex.map(acc.update, ['refill', 'withdraw'], [100, -200])

类似于mapExecutor.map每个参数采用一个可迭代,并将from each可迭代地分配给one参数。另外,在实际访问结果之前,不会传播错误。

Executor.map

类似于Executor.map(func, *iterables, timeout=None, chunksize=1) ...

如果func调用引发异常,则从迭代器中获取其值时将引发该异常。

因此,代码错误地传递了参数,但是抑制了错误。获取值,例如通过map(func, *iterables)显示错误:

list(ex.map(...))

为每种类型的参数创建单独的可迭代项可以防止这种情况。

TypeError: update() missing 1 required positional argument: 'amount'

可能希望通过调用而不是种类来对参数进行排序。使用# V transaction ex.map(acc.update, ['refill', 'withdraw'], [100, -200]) # ^ amount zip解包来按*的要求转换输入。

map

如果需要关键字参数,则需要一个助手来解压缩参数。

ex.map(acc.update, *zip(('refill', 100), ('withdraw', 200)))

[将其传递给def kwargify(func): """Wrap ``func`` to accept a dictionary of keyword arguments""" return lambda kwargs: func(**kwargs) 时,仅用该帮助器包装所需的函数:

ex.map
© www.soinside.com 2019 - 2024. All rights reserved.