两个numpy数组的笛卡尔积,条件为 [英] Cartesian product of two numpy arrays, with condition

查看:910
本文介绍了两个numpy数组的笛卡尔积,条件为的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

给出下面带有w和x的 1d 数组,我可以使用以下代码形成笛卡尔乘积。

Given 1d arrays w and x, below, I can form the Cartesian product using the following code.

import numpy as np

w = np.array([1, 2, 3, 4])
x = np.array([1, 2, 3, 4])

V1 = np.transpose([np.repeat(w, len(x)), np.tile(x, len(w))])
print(V1)

[[1 1]
 [1 2]
 [1 3]
 [1 4]
 [2 1]
 [2 2]
 [2 3]
 [2 4]
 [3 1]
 [3 2]
 [3 3]
 [3 4]
 [4 1]
 [4 2]
 [4 3]
 [4 4]]

但是,我希望输出V1包含仅数组行,其中w< x (如下所示)。我可以使用循环来完成此操作,但我希望能更快一些。

But, I want the output, V1, to include ONLY array rows where w < x (as shown below). I can do this with loops, but I'm hoping for something a little faster.

[[1 2]
 [1 3]
 [1 4]
 [2 3]
 [2 4]
 [3 4]]


推荐答案

方法#1

给出仅w< x (用于成对组合),这是实现相同的一种方法-

Given ONLY array rows where w < x, which would be for pairwise combinations, here's one way to achieve the same -

In [81]: r,c = np.nonzero(w[:,None]<x) # or np.less.outer(w,x)

In [82]: np.c_[w[r], x[c]]
Out[82]: 
array([[1, 2],
       [1, 3],
       [1, 4],
       [2, 3],
       [2, 4],
       [3, 4]])

方法2

使用纯基于掩码的方法,它是-

Using a purely masking based approach, it would be -

In [93]: mask = np.less.outer(w,x)

In [94]: s = (len(w), len(x))

In [95]: np.c_[np.broadcast_to(w[:,None], s)[mask], np.broadcast_to(x, s)[mask]]
Out[95]: 
array([[1, 2],
       [1, 3],
       [1, 4],
       [2, 3],
       [2, 4],
       [3, 4]])


基准化


使用相对较大的数组:

Benchmarking

Using comparatively larger arrays :

In [8]: np.random.seed(0)
   ...: w = np.random.randint(0,1000,(1000))
   ...: x = np.random.randint(0,1000,(1000))

In [9]: %%timeit
   ...: r,c = np.nonzero(w[:,None]<x)
   ...: np.c_[w[r], x[c]]
11.3 ms ± 24.3 µs per loop (mean ± std. dev. of 7 runs, 100 loops each)

In [10]: %%timeit
    ...: mask = np.less.outer(w,x)
    ...: s = (len(w), len(x))
    ...: np.c_[np.broadcast_to(w[:,None], s)[mask], np.broadcast_to(x, s)[mask]]
10.5 ms ± 275 µs per loop (mean ± std. dev. of 7 runs, 100 loops each)

In [11]: import itertools

# @Akshay Sehgal's soln
In [12]: %timeit [i for i in itertools.product(w,x) if i[0]<i[1]]
105 ms ± 1.38 ms per loop (mean ± std. dev. of 7 runs, 10 loops each)

这篇关于两个numpy数组的笛卡尔积,条件为的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆