首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Python itertools.product

Python itertools.product
EN

Stack Overflow用户
提问于 2014-04-23 10:12:56
回答 3查看 2.1K关注 0票数 0

我正在使用itertools包,并尝试在一个具有900个值的数组中创建1、2和3的所有可能组合,然后将其转换为一个30乘以30的矩阵。我必须这样做的代码如下所示,运行良好。

代码语言:javascript
复制
for data in itertools.product([1,2,3], repeat=900):
    datalist=list(data)
    landarray=np.asarray(datalist).reshape(30, 30)

然而,我想要做的是,使每个值(1、2和3)在900值数组中恰好出现300次。谢谢你的帮忙!

EN

回答 3

Stack Overflow用户

发布于 2014-04-23 11:49:03

您希望生成np.repeat([1,2,3], 300)多集的所有排列。There is an algorithm that allows to generate the next permutation in O(1)。下面是一个简单的算法,它使用C++ std::next_permutation() function并按字典顺序打印排列:

代码语言:javascript
复制
#!/usr/bin/env python
"""Print all multiset permutations."""
import pyximport; pyximport.install() # $ pip install cython
from next_permutation import next_permutation

n = 3
multiset = bytearray('a'*n + 'b'*n + 'c'*n)
print(multiset)
while next_permutation(multiset):
    print(multiset)

其中next_permutation模块是在Cython语言中定义的C扩展模块:

代码语言:javascript
复制
# cython: boundscheck=False
#file: next_permutation.pyx
cimport cpython.array # support array.array() on Python 2
from libcpp cimport bool

ctypedef unsigned char dtype_t
ctypedef dtype_t* Iter

cdef extern from "<algorithm>" namespace "std":
   bool cpp_next_permutation "std::next_permutation" (Iter first, Iter last)

def next_permutation(dtype_t[:] a not None):
    return cpp_next_permutation(&a[0], &a[0] + a.shape[0])

要构建它,请指定语言为C++:

代码语言:javascript
复制
#file: next_permutation.pyxbld
from distutils.extension import Extension

def make_ext(modname, pyxfilename):
    return Extension(name=modname,
                     sources=[pyxfilename],
                     language="c++")

输出

代码语言:javascript
复制
aaabbbccc
aaabbcbcc
aaabbccbc
aaabbcccb
aaabcbbcc
aaabcbcbc
aaabcbccb
aaabccbbc
aaabccbcb
aaabcccbb
aaacbbbcc
aaacbbcbc
aaacbbccb
aaacbcbbc
aaacbcbcb
aaacbccbb
..snip..
cccaabbba
cccabaabb
cccababab
cccababba
cccabbaab
cccabbaba
cccabbbaa
cccbaaabb
cccbaabab
cccbaabba
cccbabaab
cccbababa
cccbabbaa
cccbbaaab
cccbbaaba
cccbbabaa
cccbbbaaa

next_permutation()函数接受任何支持buffer接口的东西,例如,它支持numpy数组:

代码语言:javascript
复制
import numpy as np
multiset = np.repeat(np.array([1,2,3], dtype=np.uint8), 3)
票数 2
EN

Stack Overflow用户

发布于 2014-04-23 10:20:56

只需对已有均匀分布的数组进行混洗即可。

代码语言:javascript
复制
landarray = np.repeat([1,2,3], 300)
np.random.shuffle(landarray)
landarray = landarray.reshape((30,30))

我保证你不会收到重复的landarray。也就是说:您需要编辑大约10^213个landarray,然后才有50/50的机会重复一次。

票数 1
EN

Stack Overflow用户

发布于 2014-04-23 10:30:40

(咯咯笑)你知道你的代码会生成大约10**430个矩阵,对吧?

即使是受限版本也会产生大约10**426个矩阵。

你可能会在这里待很长时间。

编辑以获得规模感:

如果宇宙中的每个原子(大约10**80)

每秒可执行十亿次操作(10**18)

如果你能在每个操作中处理十亿个矩阵(10**9)

如果你用十亿个宇宙来做这个(10**9)

相当于我们宇宙当前年龄的十亿倍(大约10**26秒)

你已经达到了完成的千亿分之一。

(我开始觉得自己像卡尔·萨根;-)

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/23233616

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档