在我的程序中,我获取所有目录和文件(walk
),然后将所有目录和文件作为键和路径作为值写入字典,然后从接口({{1})获取关键字})并将所有匹配返回到两个列表。我将展示它们(tk.Entry
)并打开所选的一个(tk.Listbox
)。
我使用this一个来创建两个列表,只有一个理解。在评论中,它说“只运行两个单独的列表推导更简单,但可能更快。”所以这让我对使用哪一个感到困惑。因为这个程序将运行我现在没有的~3TB数据,所以我无法运行,看哪哪个会更快。
这是我的最小化代码,我分别删除了win32shell
,keywrd
变量的接口和定义的关键字和路径。
folder
正如我上面提到的,我的问题是在处理大量数据时哪一个会更快?
答案 0 :(得分:3)
使用zip()
:
results, paths = zip(*((k, v) for k, v in lines.items() if keywrd in k))
因为这将一步产生两个列表。另一种方法是使用一个for
循环:
results = []
paths = []
for (k,v) in lines.items():
if keywrd in k:
results.append(k)
paths.append(v)
如果你想构建一个列表,列表理解是很好的;如果您需要来自同一循环的多个,只需使用循环。
但是,由于此数据来自SQLite查询,因此最好的办法是让 SQLite 将行限制为匹配的行:
data.execute("select * from audio if filename LIKE ?", ('%{}%'.format(keywrd),))
使用词典理解可以更有效地构建lines
词典:
musics = data.execute("select * from audio")
lines = {row[1]: row[0] for row in musics}
或使用更具体的查询和光标上的直接循环:
data.execute("SELECT path, filename FROM audio WHERE filename LIKE ?",
('%{}%'.format(keywrd),))
paths, results = zip(*data)
对于两边都带有LIKE
通配符的字符串, %
会产生相同的结果,并在Python中进行in
测试;如果keywrd
中包含filename
,则匹配。
现在也不需要创建中间词典。
答案 1 :(得分:1)
更快的是使用for循环:
results = []; add_result = result.append
paths = []; add_path = path.append
for k,v in lines.items():
if keywrd in k:
add_result(k)
add_path(v)
最快的是使用你的内存中的sqlite数据库来进行过滤。