itertools.combinations生成索引组合,重复值会导致重复元组,需外层set去重;r为负数抛valueerror,r大于长度返回空迭代器;切片应用islice;permutations对重复元素产生冗余,product的repeat控制序列个数而非取元素数,所有itertools函数应避免转list以防内存溢出。

用 itertools.combinations 生成无序不重复组合时,注意输入必须可迭代且顺序影响结果
它不关心元素是否唯一,只按索引位置取值;如果原始序列有重复值(如 [1, 1, 2]),combinations([1,1,2], 2) 会返回 (1,1)、(1,2)、(1,2) —— 后两个看似相同,实则是不同索引的组合。需要去重得在外层套 set(map(tuple, ...)),但要注意元素必须是不可变类型。
- 参数
r必须是非负整数,传负数会直接抛ValueError: r must be non-negative - 若
r > len(iterable),返回空迭代器,不会报错,容易被忽略导致逻辑遗漏 - 不要试图对
combinations结果做切片(如list(...)[0:5]),应改用itertools.islice避免全量生成
用 itertools.permutations 做全排列时,重复元素会导致冗余输出
permutations('aab', 2) 返回 6 个结果,包括两组相同的 ('a','a')(来自不同位置),而实际语义上可能只需要一个。这时候不能简单用 set(),因为 permutations 返回的是 tuple,但顺序敏感 —— ('a','b') 和 ('b','a') 是不同的,不能靠集合去重。
- 如需“值唯一”的排列,先用
set对原始输入去重再传入,但会丢失原始频次信息 - 如需保留频次并去重,得配合
collections.Counter手写递归或用itertools.product+ 过滤,permutations本身不提供去重开关 - 性能上,
permutations时间复杂度是 O(n!),n 超过 10 就明显卡顿,别在循环里无节制调用
用 itertools.product 实现笛卡尔积,注意 repeat 参数和嵌套层级
它本质是多个可迭代对象的交叉遍历,product(A, B) 等价于两层 for 循环;而 product(A, repeat=3) 等价于 product(A, A, A),不是对单个列表做三次“自身组合”。常见误用是把 repeat 当成“取几个元素”,其实它控制的是参与乘积的序列个数。
Python 3.14.2是Python编程语言在2025年12月5日发布的稳定版本,属于3.14系列的第二个维护更新。该版本包含了18项修复,重点解决了多进程、数据类及正则表达式等模块的回归问题,并修复了CVE-2025-12084等安全漏洞。此版本标志着自由线程模式(移除GIL)正式获得官方支持,是Python发展的重要里程碑。
-
product(range(2), repeat=3)输出 8 个三元组,相当于 3 位二进制枚举,适合状态压缩场景 - 如果传入空列表,整个结果为空 ——
product([], repeat=2)直接返回空迭代器,不报错也不预警 - 与
combinations_with_replacement不同,product允许同一位置反复取相同元素,且顺序敏感((1,2)≠(2,1))
内存敏感场景下,避免把 itertools 结果转成 list 或 tuple
itertools 所有函数都返回迭代器,惰性求值;一旦调用 list(combinations(...)),就立刻展开全部结果到内存。对于 combinations(range(1000), 5),结果有约 8.2e+12 项,根本装不下。
- 真要遍历,直接
for c in combinations(...): process(c) - 要取前 N 个,用
islice(combinations(...), N),比list(...)[:N]省几GB内存 - 调试时想看几个样例?用
list(islice(..., 5)),别偷懒写list(...)[:5]
真正难的不是记住函数名,而是每次调用前问自己:这个结果集有多大?我是否真的需要全部?
Python免费学习笔记(深入):立即使用
在学习笔记中,你将探索 Python 的核心概念和高级技巧!










