Python 如何使扭曲的延迟操作列表真正异步

Python 如何使扭曲的延迟操作列表真正异步,python,twisted,twisted.internet,Python,Twisted,Twisted.internet,我是使用Twisted库的新手,我想创建一个异步操作列表。以以下伪代码为例: @defer.inlineCallbacks def getDataAsync(host): data = yield AsyncHttpAPI(host) # some asyc api which returns deferred return data @defer.inlineCallbacks def funcPrintData(): hosts = []; # some l

我是使用Twisted库的新手,我想创建一个异步操作列表。以以下伪代码为例:

@defer.inlineCallbacks
def getDataAsync(host):
    data = yield AsyncHttpAPI(host) # some asyc api which returns deferred
    return data
    
@defer.inlineCallbacks
def funcPrintData():
    hosts = []; # some list of hosts, say 1000 in number
    for host in hosts:
        data = yield getDataAsync(host)
        # why doesn't the following line get printed as soon as first result is available
        # it waits for all getDataAsync to be queued before calling the callback and so print data
        print(data)
如果问题不清楚,请发表评论。有更好的方法吗?我应该改为使用延迟列表吗?

行:

data = yield getDataAsync(host)
表示“停止运行此函数,直到
getDataAsync(主机)
操作完成。如果该函数停止运行,则
for
循环无法进入任何后续迭代,因此这些操作在第一次
getDataAsync(主机)之后才能开始”
已完成。如果要同时运行所有操作,则在所有操作开始之前不需要停止运行函数。例如:

ops = []
for host in hosts:
    ops.append(getDataAsync(host))
运行此操作后,所有操作都将开始,无论是否有任何操作已完成

如何处理
ops
取决于您是否希望结果的顺序与
hosts
相同,或者您是否希望在所有结果准备就绪时一次将它们全部显示出来,或者您是否希望按照操作成功的顺序一次显示一个结果

DeferredList
用于在它们以与输入列表相同的顺序作为列表准备就绪时立即获取它们(
ops
):

如果希望在每个结果可用时对其进行处理,则使用
addCallback
更容易:

ops = []
for host in hosts:
    ops.append(getDataAsync(host).addCallback(print))

这仍然不会产生,因此整个操作组都会启动。但是,每个操作有结果时,回调就会立即运行。在
ops
中,您仍然会留下一个
延迟的
实例列表,如果需要或附加ove,您仍然可以使用该列表等待所有结果完成rall错误处理到(至少其中一个是一个好主意,否则您有一些悬空操作,在
funcPrintDat
的调用者中很难解释).

谢谢你的回答,因为我提到了主机的数量是以千为单位的,我如何限制并发调用的数量,这样我就不会遇到超时/连接之类的问题。我想开始,比如说100个并发操作,然后如果有一个操作完成了,我想在列表中添加另一个操作,依此类推E
ops = []
for host in hosts:
    ops.append(getDataAsync(host).addCallback(print))