Python 当指定总数时,tqdm 在迭代之前退出

Python tqdm quits before iterating when total is specified

我一直在寻找进度条解决方案并遇到了 tqdm。将它集成到我的程序中并按照示例进行操作后,它 运行 可以很好地处理我指定的可迭代对象,但最初没有显示进度条。我发现我使用的 iterable 不支持 len。我修改了代码,以便手动指定 total 参数,现在,运行 循环导致程序在进度为 0% 时退出。以下是带有输出的初始和修改后的代码:

初始代码:

import pathlib
from tqdm import tqdm

paths = pathlib.Path('F://Music').rglob('*.mp3')

for f in tqdm(paths):
    # do stuff that takes time
    print(f.name) # prints ok

初始输出:320it [00:00, 25528.56it/s]

修改后的代码:

import pathlib
from tqdm import tqdm

paths = pathlib.Path('F://Music').rglob('*.mp3')

cnt = 0
for p in paths: cnt += 1

for f in tqdm(paths, total=cnt):
    # do stuff that takes time
    print(f.name) # line not reached

新输出:0%| | 0/320 [00:00<?, ?it/s]

在这种情况下指定 total 似乎会破坏它,即使总数是正确的。

paths = pathlib.Path('F://Music').rglob('*.mp3')定义的变量paths不是一个类似列表的数据结构,而是一个generator.

当您迭代它以在变量 cnt 中获取它的长度时,您耗尽了生成器,并且当您第二次尝试从中获取数据时(当您使用 tqdm ),该数据不再存在。

将生成器转换为列表的一种方法是进行实际转换,即 paths_list = list(paths),然后对其调用 tqdm。如果您的 paths 变量包含大量数据,这可能不是最佳解决方案。


此代码应该可以正常工作:

import pathlib
from tqdm import tqdm

paths = pathlib.Path('F://Music').rglob('*.mp3')
paths_list = list(paths)

for f in tqdm(paths_list):
    print(f.name)