我有以下代码在芹菜任务中运行,self.resdict['jobs'] 包含一个子任务列表,我正在 while 循环中检查它们的状态。
while any([x.status for x in self.resdict['jobs'].values() if x.status is not 'SUCCESS']):
print([x.status for x in self.resdict['jobs'].values() if x.status is not 'SUCCESS'])
print(any([x.status for x in self.resdict['jobs'].values() if x.status is not 'SUCCESS']))
time.sleep(.5)
else:
for a in self.resdict['accounts'][0]['result']:
account = a['number'] if isinstance(a['number'], str) else False
self.resdict[account] = self.resdict['jobs'][account].result[0]['result'][0]['Device Information']['subattributes']
当我使用 CELERY_ALWAYS_EAGER = True 和 CELERY_EAGER_PROPAGATES_EXCEPTIONS = True 运行此代码时,如果列表包含所有"SUCCESS",它会给我预期的结果
所以当我总是急切地跑步时,我得到的是:
print([x.status for x in self.resdict['jobs'].values() if x.status is not 'SUCCESS']) = ['SUCCESS', 'SUCCESS', 'SUCCESS', 'SUCCESS', 'SUCCESS', 'SUCCESS', 'SUCCESS', 'SUCCESS', 'SUCCESS', 'SUCCESS', 'SUCCESS', 'SUCCESS', 'SUCCESS', 'SUCCESS', 'SUCCESS', 'SUCCESS', 'SUCCESS']
print(any([x.status for x in self.resdict['jobs'].values() if x.status is not 'SUCCESS'])) = False
当我不总是急切地运行时,在芹菜调试中,我看到:
print([x.status for x in self.resdict['jobs'].values() if x.status is not 'SUCCESS']) = ['SUCCESS', 'SUCCESS', 'SUCCESS', 'SUCCESS', 'SUCCESS', 'SUCCESS', 'SUCCESS', 'SUCCESS', 'SUCCESS', 'SUCCESS', 'SUCCESS', 'SUCCESS', 'SUCCESS', 'SUCCESS', 'SUCCESS', 'SUCCESS', 'SUCCESS']
print(any([x.status for x in self.resdict['jobs'].values() if x.status is not 'SUCCESS'])) = True
这是不正确的,因为列表仅包含"成功"。
知道为什么芹菜说真,而它应该是假的吗?
您不应该将字符串与is
进行比较。它有时可能会起作用,因为某些字符串将被 Python 解释器"暂留"和缓存,但这种缓存并不能保证在所有情况下都发生。相反,您应该按值而不是标识进行比较,使用==
而不是is
和!=
代替is not
。
这应该可以解决您当前的问题,但我进一步建议您似乎没有以非常有用的方式使用any
。any
函数在其可迭代参数中的第一个值为 true 后返回True
。如果您只想测试空列表,请跳过any
,仅将列表本身用作布尔值。空列表是假的,而包含任何元素的列表(无论这些元素的值如何(都是真实的。
如果您一开始不构建列表,使用any
会更有意义。这是因为any
短路,在第一个真实结果后停止,而不检查其余的可迭代对象。这使得它与生成器很好地匹配,生成器懒惰地计算其值,只根据需要计算。您可以将列表推导式替换为生成器表达式,只需删除方括号即可。但在这种情况下,我建议更改您的代码,以便生成器产生bool
s 而不是值或什么都没有:any(x.status != "Success" for x in self.resdict['jobs'].values())