Python3 - 排列组合的迭代

问题

遍历一个序列中元素的所有可能的排列或组合。

解决方案

itertools模块提供了三个函数来解决这类问题。 其中一个是 itertools.permutations(), 它接受一个序列并产生一个元组序列,每个元组由序列中所有元素的一个可能排列组成,即通过打乱序列中元素排列顺序生成一个元组,比如:

from itertools import permutations

items = ['a', 'b', 'c']
for p in permutations(items):
    print(p)

('a', 'b', 'c')
('a', 'c', 'b')
('b', 'a', 'c')
('b', 'c', 'a')
('c', 'a', 'b')
('c', 'b', 'a')

如果想得到指定长度的所有排列,你可以传递一个可选的长度参数。比如:

for p in permutations(items, 2):
    print(p)

('a', 'b')
('a', 'c')
('b', 'a')
('b', 'c')
('c', 'a')
('c', 'b')

使用 itertools.combinations() 可得到输入序列中元素的所有的组合。比如:

for c in combinations(items, 3):
    print(c)
('a', 'b', 'c')

for c in combinations(items, 2):
    print(c)
('a', 'b')
('a', 'c')
('b', 'c')

for c in combinations(items, 1):
    print(c)
('a',)
('b',)
('c',)

对于 combinations() 来讲,元素的顺序已经不重要了,即组合 ('a', 'b') 与 ('b', 'a') 其实是一样的,最终只会输出其中一个。

在计算组合的时候,一旦元素被选取就会从候选中剔除掉(比如如果元素’a’已经被选取了,那么接下来就不会再考虑它了)。 而函数 itertools.combinations_with_replacement()允许同一个元素被选择多次,比如:

from itertools import combinations_with_replacement

for c in combinations_with_replacement(items, 3):
    print(c)

('a', 'a', 'a')
('a', 'a', 'b')
('a', 'a', 'c')
('a', 'b', 'b')
('a', 'b', 'c')
('a', 'c', 'c')
('b', 'b', 'b')
('b', 'b', 'c')
('b', 'c', 'c')
('c', 'c', 'c')

讨论

尽管手动可以实现排列组合算法,但是这样做比较麻烦,当遇到有些复杂的迭代问题时,可以先去看看itertools模块是否能实现,很有可能会在里面找到解决方案!

©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容

  • PYTHON-进阶-ITERTOOLS模块小结转自wklken:http://wklken.me/posts/20...
    C_Y_阅读 4,704评论 0 2
  • 问题:想对一系列元素所有可能的组合或排列进行迭代 1、itertools.permutations() 它接受一个...
    cook__阅读 4,430评论 0 1
  • 4.1 手动遍历迭代器 你想遍历一个可迭代对象中的所有元素,但是却不想使用for循环。 为了手动的遍历可迭代对象,...
    czm123阅读 2,271评论 0 0
  • 1 itertools函数 以下模块级别函数都构造并返回iterator。有些iterator是无限长度的流,因此...
    lakerszhy阅读 4,724评论 0 3
  • 在这个世界上有很多美丽的景色,但黄龙五彩池却不一样,它对我来说有一种特殊的感觉,也有一种特殊的回忆…… 我们一家人...
    WXYWJY阅读 3,064评论 0 0