Python Numpy:基于单独向量交换二维数组的位置

Python Numpy:基于单独向量交换二维数组的位置,python,arrays,numpy,matrix,Python,Arrays,Numpy,Matrix,假设我有一个3x3 numpy阵列: [[0, 1, 2], [2, 0, 1], [1, 2, 0]] 还有一个向量: [2, 1, 1] 对于矩阵中的每一行,我想将第0个索引处的数字与向量中相应索引处的数字交换。在本例中,交换后,最终输出为: [[2, 1, 0], # the 0th and 2nd positions have been swapped [0, 2, 1], # the 0th and 1st positions have been swapped [2,

假设我有一个3x3 numpy阵列:

[[0, 1, 2],
 [2, 0, 1],
 [1, 2, 0]]
还有一个向量:

[2,
 1,
 1]
对于矩阵中的每一行,我想将第0个索引处的数字与向量中相应索引处的数字交换。在本例中,交换后,最终输出为:

[[2, 1, 0], # the 0th and 2nd positions have been swapped
 [0, 2, 1], # the 0th and 1st positions have been swapped
 [2, 1, 0]] # the 0th and 1st positions have been swapped
你怎么能做到这一点

a= np.array([[0,1,2],[2,0,1],[1,2,0]])
b=[2,1,1]
for rc, r in enumerate(a):
    r[0], r[b[rc]] =  r[b[rc]], r[0]
print(a)
或者更简洁地说

c = np.asarray([2, 1, 1])
r = np.arange(len(A))
A[:, 0], A[r, c] = A[r, c], A[:, 0].copy()
在这里,我们利用了这样一个事实:我们可以通过为numpy数组提供两个单独的类似列表的对象来为相应的行和列索引,从而为numpy数组的各个元素建立索引

因此,可以将行
A[:,0],A[r,c]=A[r,c],A[:,0].copy()读取为从每列获取索引元素并与第一列交换

编辑 多亏了@Paul Panzer的评论,通过将作业写成
A[r,c],A[:,0]=A[:,0],A[r,c]
,可以使作业变得更短

请注意,与早期版本相比,
A[r,c]
A[:,0]
的赋值顺序已更改

此处可以省略副本的原因是

  • 在作业中,右手边在作业开始前会被完全评估 分配给左边的变量
  • Numpy的奇特索引(
    A[r,c]
    here)返回一个不同于 返回视图的切片(
    A[:,0]
  • 因此,这行新代码所说的是

  • 获取
    a
  • 创建
    a[r,c]
    的副本。副本是隐式的,因为Numpy数组的索引非常奇特
  • 使用 该列的视图
  • 将前面制作的
    A[r,c]
    的副本分配给
    A的第一列
    (注意,此时,
    A[r,c]
    已被分配旧的
    A[:,0]
    的值
  • 此外,我们不需要将索引转换为Numpy数组

    c = [2, 1, 1]
    r = range(len(A))
    A[r, c], A[:, 0] = A[:, 0], A[r, c]
    

    x[[0,1,2],[2,1,1]],x[[0,1,2],[0,0,0]]=x[[0,1,2],[0,0,0]],x[[0,1,2],[2,1,1]]
    或更短的
    A[r,c],A[:,0]=A[:,0],A[r,c]
    使用
    A[r,c]
    复制的事实。@PaulPanzer No.
    A[/code>A[/0]以片段的形式返回视图,所以副本是必要的。@PaulPanzer哦,是的,你是对的。忽略我之前的评论。我没看到你改变了任务的顺序。
    
    c = [2, 1, 1]
    r = range(len(A))
    A[r, c], A[:, 0] = A[:, 0], A[r, c]