![](/img/trans.png)
[英]Row-wise replacement of numpy array with values of another numpy array
[英]How to randomly assign values row-wise in a numpy array
我的Google Fu使我失败了! 我有一个10x10的numpy数组,初始化为0
,如下所示:
arr2d = np.zeros((10,10))
对于arr2d
每一行,我想将3个随机列分配给1
。 我可以使用如下循环来做到这一点:
for row in arr2d:
rand_cols = np.random.randint(0,9,3)
row[rand_cols] = 1
输出:
array([[ 0., 0., 0., 0., 0., 0., 1., 1., 1., 0.],
[ 0., 0., 0., 0., 1., 0., 0., 0., 1., 0.],
[ 0., 0., 1., 0., 1., 1., 0., 0., 0., 0.],
[ 0., 0., 0., 0., 1., 1., 1., 0., 0., 0.],
[ 1., 0., 0., 1., 1., 0., 0., 0., 0., 0.],
[ 1., 0., 1., 1., 0., 0., 0., 0., 0., 0.],
[ 0., 1., 0., 0., 0., 0., 1., 0., 1., 0.],
[ 0., 0., 1., 0., 1., 0., 0., 0., 1., 0.],
[ 1., 0., 0., 0., 0., 0., 1., 1., 0., 0.],
[ 0., 1., 0., 0., 1., 0., 0., 1., 0., 0.]])
有没有一种方法可以利用numpy或数组索引/切片以更pythonic /优雅的方式(最好在1或2行代码中)获得相同的结果?
一旦你的arr2d
与初始化arr2d = np.zeros((10,10))
您可以使用矢量方法有two-liner
像这样-
# Generate random unique 3 column indices for 10 rows
idx = np.random.rand(10,10).argsort(1)[:,:3]
# Assign them into initialized array
arr2d[np.arange(10)[:,None],idx] = 1
或者,如果您喜欢那样的话,可以抽成一排的所有物品:
arr2d[np.arange(10)[:,None],np.random.rand(10,10).argsort(1)[:,:3]] = 1
样品运行-
In [11]: arr2d = np.zeros((10,10)) # Initialize array
In [12]: idx = np.random.rand(10,10).argsort(1)[:,:3]
In [13]: arr2d[np.arange(10)[:,None],idx] = 1
In [14]: arr2d # Verify by manual inspection
Out[14]:
array([[ 0., 1., 0., 1., 0., 0., 0., 0., 1., 0.],
[ 0., 0., 0., 0., 1., 1., 0., 0., 1., 0.],
[ 0., 0., 0., 0., 0., 1., 0., 1., 0., 1.],
[ 0., 1., 1., 0., 0., 0., 0., 0., 1., 0.],
[ 0., 0., 1., 1., 0., 0., 0., 1., 0., 0.],
[ 1., 0., 0., 0., 0., 1., 0., 0., 1., 0.],
[ 0., 0., 0., 1., 0., 0., 0., 1., 0., 1.],
[ 1., 0., 0., 0., 0., 0., 1., 0., 1., 0.],
[ 1., 0., 0., 1., 0., 0., 0., 0., 1., 0.],
[ 0., 1., 0., 1., 0., 0., 0., 0., 0., 1.]])
In [15]: arr2d.sum(1) # Verify by counting ones in each row
Out[15]: array([ 3., 3., 3., 3., 3., 3., 3., 3., 3., 3.])
注意:如果您正在寻找性能,我建议您使用np.argpartition
this other post
列出的基于np.argpartition
的方法。
使用此问题的答案来生成非重复的随机数。 您可以使用random.sample
从Python的random
模块,或np.random.choice
。
因此,只需对您的代码进行少量修改:
>>> import numpy as np
>>> for row in arr2d:
... rand_cols = np.random.choice(range(10), 3, replace=False)
... # Or the python standard lib alternative (use `import random`)
... # rand_cols = random.sample(range(10), 3)
... row[rand_cols] = 1
...
>>> arr2d
array([[ 0., 0., 0., 0., 0., 1., 1., 1., 0., 0.],
[ 0., 0., 1., 0., 0., 0., 0., 0., 1., 1.],
[ 1., 0., 0., 0., 0., 0., 1., 0., 1., 0.],
[ 0., 0., 1., 1., 0., 0., 1., 0., 0., 0.],
[ 0., 0., 0., 0., 0., 0., 1., 0., 1., 1.],
[ 0., 0., 1., 1., 0., 0., 1., 0., 0., 0.],
[ 0., 0., 0., 0., 1., 1., 1., 0., 0., 0.],
[ 0., 1., 0., 0., 1., 1., 0., 0., 0., 0.],
[ 0., 1., 0., 0., 1., 0., 0., 0., 1., 0.],
[ 0., 0., 1., 1., 0., 0., 0., 0., 1., 0.]])
我不认为您真的可以利用此处的列切片将值设置为1,除非您是从头开始生成随机数组。 这是因为您的列索引对于每一行都是随机的 。 您最好将其以循环的形式保留,以提高可读性。
我不确定这在性能方面有多好,但是相当简洁。
arr2d[:, :3] = 1
map(np.random.shuffle, arr2d)
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.