Python使用itertools.product时repeat≥5程序冻结,求通用优化方案
问题原因
你的代码冻结是内存爆炸直接导致的:
- 字符集
u的长度是95,repeat=5时排列组合总数是95^5 = 7737809375,接近80亿条结果 - 你写了
c=list(itertools.product(u,repeat=5)),直接把迭代器转成列表,会强制把所有80亿条结果一次性加载到内存,普通家用机的内存完全装不下,自然会直接冻结无响应 - 后续
print(list(r))又是一次无意义的全量遍历+列表生成,进一步放大了内存和性能消耗,main函数没有返回值,生成的全是None的列表没有任何作用
优化方案
直接使用itertools返回的迭代器本身,不做列表转换,内存占用会稳定在常数级,同时优化IO写入效率,代码如下:
import itertools # 缓冲区大小,每攒10万条写入一次,可根据自己内存调整 BATCH_SIZE = 100000 def main(): u = list(map(chr, range(32, 127))) buffer = [] # 用with上下文管理自动处理文件关闭,避免异常时文件损坏 with open("pp.txt", "w", encoding="utf-8") as s: for idx, item in enumerate(itertools.product(u, repeat=5)): # product返回的本身就是可迭代的元组,不需要额外转tuple result = ''.join(item) buffer.append(f"{result},") # 达到批次大小就写入清空缓冲区,减少磁盘IO次数 if len(buffer) >= BATCH_SIZE: s.write(''.join(buffer)) buffer.clear() # 可选打印进度,方便确认运行状态 # print(f"已处理:{idx+1}条") # 写入最后剩余的缓冲区内容 if buffer: s.write(''.join(buffer)) if __name__ == "__main__": main()
补充说明
repeat=5时80亿条数据就算每秒处理10万条,也需要200多小时才能跑完,生成的文件大小会超过350G,建议根据实际需求限制字符集范围或者repeat大小- 可以根据自己的硬件配置调整BATCH_SIZE,数值越大写入效率越高,内存占用也会相应提升
内容的提问来源于stack exchange,提问作者Rahat Bin Taleb
相关产品推荐
相关产品推荐

