Giải pháp:
>>> a[np.arange(np.shape(a)[0])[:,np.newaxis], np.argsort(a)]
array([[1, 2, 3],
[2, 8, 9]])
Bạn đã làm đúng, mặc dù tôi sẽ không mô tả nó như gian lận việc lập chỉ mục.
Có lẽ điều này sẽ giúp làm cho nó rõ ràng hơn:
In [544]: i=np.argsort(a,axis=1)
In [545]: i
Out[545]:
array([[1, 2, 0],
[2, 0, 1]])
i
là thứ tự mà chúng ta muốn, cho mỗi hàng. Đó là:
In [546]: a[0, i[0,:]]
Out[546]: array([1, 2, 3])
In [547]: a[1, i[1,:]]
Out[547]: array([2, 8, 9])
Để thực hiện cả hai bước lập chỉ mục cùng một lúc, chúng tôi phải sử dụng chỉ mục 'cột' cho thứ nguyên thứ nhất.
In [548]: a[[[0],[1]],i]
Out[548]:
array([[1, 2, 3],
[2, 8, 9]])
Một mảng có thể được ghép nối với i
là:
In [560]: j=np.array([[0,0,0],[1,1,1]])
In [561]: j
Out[561]:
array([[0, 0, 0],
[1, 1, 1]])
In [562]: a[j,i]
Out[562]:
array([[1, 2, 3],
[2, 8, 9]])
Nếu i
xác định các cột cho mỗi phần tử, sau đó j
xác định hàng cho mỗi yếu tố. Mảng cột [[0],[1]]
hoạt động tốt bởi vì nó có thể được phát sóng với i
.
tôi nghĩ về
np.array([[0],
[1]])
là 'tay ngắn' cho j
. Họ cùng nhau xác định hàng và cột nguồn của mỗi phần tử của mảng mới. Họ làm việc cùng nhau, không phải tuần tự.
Việc lập bản đồ đầy đủ từ a
đến các mảng mới là:
[a[0,1] a[0,2] a[0,0]
a[1,2] a[1,0] a[1,1]]
def foo(a):
i = np.argsort(a, axis=1)
return (np.arange(a.shape[0])[:,None], i)
In [61]: foo(a)
Out[61]:
(array([[0],
[1]]), array([[1, 2, 0],
[2, 0, 1]], dtype=int32))
In [62]: a[foo(a)]
Out[62]:
array([[1, 2, 3],
[2, 8, 9]])
Cảm ơn @hpaulj, giải thích thực sự hữu ích! Nếu bạn có giây, bạn có thể giải thích 'chỉ mục cột [ing] cho thứ nguyên thứ nhất' không? Đó chỉ là chuyển đổi mảng sang một quyền (2.1,3) ... tại sao điều đó lại tạo điều kiện cho việc cắt 'i'? – DilithiumMatrix
Tôi mở rộng lời giải thích của mình. – hpaulj
có cách nào đơn giản hơn để thực hiện việc này không? tôi nghĩ rằng các argsort nên đã xem xét những gì nó sẽ được sử dụng cho sau khi phân loại các mảng? ..... – Martian2049