2013-09-05 3 views
2

파이썬에서 벡터 배열의 데카르트 곱으로 볼 수있는 것을 생성하는 데 문제가 있습니다. r 변수보다 n 개의 가능한 모든 파티션을 제공하는 코드를 가지고 있으며이를 numpy 배열로 반환합니다. 내가하고 싶은 것은 그 코드를 임의의 횟수만큼 호출하고 배열의 모든 가능한 조합의 집합을 생성 할 수있는 것입니다. 파이썬에서 모든 벡터 조합 세트

그래서 예를 제공하기 위해, 나는 집합을 반환 할 수 있도록 내가 무엇을 찾고 파티션 코드 (변화하는 매개 변수 세트) 각 연속 호출

array([[2,0],[1,1],[2,0]]) 
array([[1,0],[0,1]]) 
array([[0,0]]) 

입니다 호출 할 수

array([[2,0],[1,0],[0,0]]) 
array([[2,0],[0,1],[0,0]]) 
array([[1,1],[1,0],[0,0]]) 
..... 

전체 배열 또는 줄 단위로 반환합니다 (분할되는 숫자의 크기가 커짐에 따라 명백한 메모리 문제가 발생 함).

이전에 itertools.product를 사용하여이 문제를 해결하고 PyPy에서 코드를 실행했습니다. 그러나 프로젝트의 다른 부분에서 Numpy가 필요하기 때문에 PyPy에서 표준 Python으로 전환해야했으며 Numpy를 사용하여 PyPy 코드의 속도를 재현하려고합니다. 나는이 작업을 대략적으로 처리 할 수 ​​있었지만, 코드는 솔루션을 함께 부트 스트랩하여 구현하기에는 너무 비싸다.

아무도 내가 이것을 파이썬으로 어떻게 진행해야하는지에 대한 약간의 지침을 제공해 주실 수 있는지 궁금합니다.

감사

+0

numpy 명령을 사용하여 외부 제품을 구축하고 있습니까? 코드를 제공 할 수 있습니까? –

+0

는 생성 된 분할 코드를 의미 말아 어레이 ([2,0], [1,1], [2,0]) 어레이 ([1,0], [0,1]) 배열 ([[0,0]]) – user2745293

답변

1

이 당신은 시작해야

import numpy as np 
import itertools as it 

def row_product(*arrays): 
    lengths = np.array([x.shape[0] for x in arrays]) 
    positions = np.cumsum(lengths) 

    ranges = np.arange(positions[-1]) 
    ranges = np.split(ranges,positions[:-1]) 

    total = np.concatenate((arrays),axis=0) 

    inds = np.fromiter(it.chain.from_iterable(it.product(*ranges)), np.int) 
    inds = inds.reshape(-1, len(arrays)) 

    return np.take(total, inds, axis=0) 

마지막 차원 (들)이 동일해야합니다.

나타내는 결과

a=np.array([[2,0],[1,1],[2,0]]) 
b=np.array([[1,0],[0,1]]) 
c=np.array([[0,0]]) 

print row_product(a,b,c) 

[[[2 0] 
    [1 0] 
    [0 0]] 

[[2 0] 
    [0 1] 
    [0 0]] 

[[1 1] 
    [1 0] 
    [0 0]] 

[[1 1] 
    [0 1] 
    [0 0]] 

[[2 0] 
    [1 0] 
    [0 0]] 

[[2 0] 
    [0 1] 
    [0 0]]] 

이 고유 조합의 마지막 두 개의 축에있는 3 차원 배열이다. 합리적으로 빠른 것 같습니다. 1M 고유 조합은 약 1/6 초가 걸립니다.

+0

고맙습니다! 그러나 내가 겪어 본 한 가지 문제점은 입력 인수의 임의의 집합에 대해이를 호출하는 방법입니다. 예를 들어, row_product (row_product (a, b), c) 또는 row_product ([xrange (4)의 i에 대해 [composition (i, 2)])를 호출하려고 시도했지만 호출 할 수없는 것 같습니다. 아마 바보 같은 질문 일 겁니다.하지만 배열을 row_product에 전달하는 가장 좋은 방법은 무엇입니까? – user2745293

+0

'row_product (배열)'을'row_product (배열)'과'np.concatenate ((배열), axis = 0)'을'np.concatenate (배열, 축 = 0)'. – Daniel

+0

이 오피온에 협조 해 주셔서 대단히 감사합니다. 나는이 문제 (또는 어쨌든 이것을 통합하는 더 큰 문제)를 몇 주 동안 돌렸고, 정말로 이것에 시간을 내 주셔서 감사합니다. – user2745293