我需要找到一个numpy数组中忽略对角元素后的最大值。
np.amax() 提供了忽略特定轴的方法。如何忽略所有对角线元素并达到同样的效果?
你可以使用口罩
mask = np.ones(a.shape, dtype=bool)
np.fill_diagonal(mask, 0)
max_value = a[mask].max()
其中a
是您要查找最大值的矩阵。掩码选择了非对角线元素,因此a[mask]
将是所有非对角线元素的长向量。然后,您只需取最大值。
或者,如果您不介意修改原始数组
np.fill_diagonal(a, -np.inf)
max_value = a.max()
当然,您始终可以复制原始数据,然后在不修改原始数据的情况下执行上述操作。此外,这是建立在a
为某种浮点格式的假设之上。as_strided
将对角线推到第一列,然后再将其切片:import numpy as np
from numpy.lib.stride_tricks import as_strided
b = np.arange(0,25,1).reshape((5,5))
n = b.shape[0]
out = np.max(as_strided(b, (n-1,n+1), (b.itemsize*(n+1), b.itemsize))[:,1:])
对于类似于下面的 b
:
array([[ 0, 1, 2, 3, 4],
[ 5, 6, 7, 8, 9],
[10, 11, 12, 13, 14],
[15, 16, 17, 18, 19],
[20, 21, 22, 23, 24]])
23
np.max
函数的参数是针对b
的移位视图:
In [7]: as_strided(b, (n-1,n+1), (b.itemsize*(n+1), b.itemsize))
Out[7]: array([[ 0, 1, 2, 3, 4, 5],
[ 6, 7, 8, 9, 10, 11],
[12, 13, 14, 15, 16, 17],
[18, 19, 20, 21, 22, 23]])
这样做的目的是:
In [8]: as_strided(b, (n-1,n+1), (b.itemsize*(n+1), b.itemsize))[:,1:]
Out[8]: array([[ 1, 2, 3, 4, 5],
[ 7, 8, 9, 10, 11],
[13, 14, 15, 16, 17],
[19, 20, 21, 22, 23]])
m
个 n
xn
数组的数组:np.max(as_strided(c, (m,n-1,n+1), (c.itemsize*n*n, c.itemsize*(n+1), c.itemsize))[:,:,1:], axis=(1,2))
:为了得到更好的答案,我认为你应该提出一个新问题。 - xnximport numpy as np
import numpy.random
# create sample matrix
a = numpy.random.randint(10,size=(8,8))
a[0,0] = 100
array([[100, 8, 6, 5, 5, 7, 4, 5],
[4, 6, 1, 7, 4, 5, 8, 5],
[0, 2, 0, 7, 4, 2, 7, 9],
[5, 7, 5, 9, 8, 3, 2, 8],
[2, 1, 3, 4, 0, 7, 8, 1],
[6, 6, 7, 6, 0, 6, 6, 8],
[6, 0, 1, 9, 7, 7, 9, 3],
[0, 5, 5, 5, 1, 5, 4, 4]])
# create mask
mask = np.ones((8,8))
mask = (mask - np.diag(np.ones(8))).astype(np.bool)
看起来像这样:
array([[False, True, True, True, True, True, True, True],
[ True, False, True, True, True, True, True, True],
[ True, True, False, True, True, True, True, True],
[ True, True, True, False, True, True, True, True],
[ True, True, True, True, False, True, True, True],
[ True, True, True, True, True, False, True, True],
[ True, True, True, True, True, True, False, True],
[ True, True, True, True, True, True, True, False]], dtype=bool)
那么
# calculate the maximum
out = np.amax(a[mask])
输出:
9
row_mins = np.where(np.eye(*a.shape, dtype=bool), a.max(), a).min(axis=1)
对于沿轴的max
,将其改为min
,反之亦然:
row_maxs = np.where(np.eye(*a.shape, dtype=bool), a.min(), a).max(axis=1)
另一种选择是将数组最大值添加到对角线上的值中,并沿着一个轴找到min
(将max
减去):
row_mins = (a+np.diag([a.max()]*len(a))).min(axis=1)
row_maxs = (a-np.diag([a.max()]*len(a))).max(axis=1)
示例:
对于数组:
array([[ 0, 1, 2, 3, 4],
[ 5, 6, 7, 8, 9],
[10, 11, 12, 13, 14],
[15, 16, 17, 18, 19],
[20, 21, 22, 23, 24]])
的输出
out = np.where(np.eye(*a.shape, dtype=bool), a.max(), a).min(axis=1)
是
array([ 1, 5, 10, 15, 20])
a[~np.eye(*a.shape, dtype=bool)].max()
。 - user76284