如何从某个条件定义的子集中找到值的原始索引?

2024-04-25 09:40:32 发布

您现在位置:Python中文网/ 问答频道 /正文

我有一个数组的值,我想做一些形式的梯度下降/上升从一个随机的起点。如果我有一个值矩阵,比如:

board = np.array([[ 2.41791045, -1.70149254, -1.85074627, -1.46268657,],
                  [-1.70149254, -1.91044776, -1.94029851, -1.85074627],
                  [-1.85074627, -1.94029851, -1.91044776, -1.70149254],
                  [-1.46268657, -1.85074627, -1.70149254,  2.41791045]])

我想对随机起始索引的4个直接邻居进行采样,并返回最大索引的索引。我可以用起始索引-1,+1循环两次,很容易地对邻居进行采样。你知道吗

如何找到原始数组的索引,而不是为了找到最大值而采样的值?在原始数组中搜索计算出的最大值并不总是有效的,因为正如您在我的示例中看到的,数组是对称的。你知道吗

我应该说,我真的不想为每个方向手动创建if语句,因为我想让它尽可能的通用,以后我可能希望能够采样其他网站或移动到三维。你知道吗

编辑: 对不起,如果我在原来的帖子里不是很清楚的话。最终的目标是通过板向下移动值的梯度,直到到达一个出口点(在这种情况下,右上角和左下角)。例如,如果我从位置(2,3)开始,给定例子中的值是-1.701459。然后我想知道周围4个值中哪个最高,更重要的是索引是什么。我将采样的4个值是从上、下、左、右(带包装)开始的。因此,如果我从位置(2,3)开始,4个采样值将是board[1,3],board[3,3],board[2,2]和board[2,0]。你知道吗

如果我想先将它们保存到一个单独的数组中,我将使用以下代码:

size = 4
start = np.random.randint(1, size - 1, 2)

samples = []
for x in (-1, 1):
    samples = np.append(samples, board[(start[0] + x) % size, start[1]])
for y in (-1, 1):
    samples = np.append(samples, board[start[0], (start[1] + y) % size])

optimalMove = max(samples)

然而,我不只是想要最大值的值,我想知道它在数组“board”中的位置,但我不知道如何做到这一点。你知道吗

最终编辑: 我已经解决了我的问题!你知道吗

对于那些好奇我是怎么做到的人: 首先我创建了一个与我的电路板形状相同的布尔掩码,然后我设置了所有我不想认为是NaN的值。举个例子:

[[ 2.41791045         nan         nan         nan]
 [        nan -1.91044776         nan -1.85074627]
 [-1.85074627         nan         nan         nan]
 [        nan         nan         nan         nan]]

最后,我使用numpy的nanmax命令确定了最大值,并使用np.哪里. 这也允许我创建一个包含所有等价邻居的数组,并从中随机选择。代码如下:

mask = np.ones_like(valueMatrix, dtype=bool)
for x in (-1, 1):
    mask[start[1], (start[0] + x) % size] = False
for y in (-1, 1):
    mask[(start[1] + y) % size, start[0]] = False

mask = mask.flatten()  # Flatten because np.nanmax() requires 1D arrays
dummyVal = valueMatrix.copy().flatten()
dummyVal[mask] = np.NaN
print(np.reshape(dummyVal, (size, size)))
position = np.where(dummyVal == np.nanmax(dummyVal))[0]

if len(position) > 1:  # Make sure only one value is chosen (at random)
    position = int(np.random.choice(position))

# These calculations convert the position value into co-ordinates to be used 
# as indices for the next move.
start = np.array([int(position % size), (int((position / size)))])

#  this whole thing goes in a while loop that continues until some exit 
#  position is landed on

Tags: inboardforsizenppositionmaskrandom
1条回答
网友
1楼 · 发布于 2024-04-25 09:40:32

你能从分享一些你尝试过的代码开始吗。 而且,你的目标我也不太清楚。 你想采样4个邻居(我想总共有5个样本来自i-2:i+2)?。 要从该集中检索最大样本的索引吗?你知道吗

如果这是正确的,我会这样做。你知道吗

import numpy as np

# assuming idx is the desired index
def sample(board,idx, win):
    # creating a dummy variable here. You don't need this for your code
    board = np.array([[2.41791045, -1.70149254, -1.85074627, -1.46268657, ],
        [-1.70149254, -1.91044776, -1.94029851, -1.85074627],
        [-1.85074627, -1.94029851, -1.91044776, -1.70149254],
        [-1.46268657, -1.85074627, -1.70149254, 2.41791045]])

    tmp = idx - win + np.argmax(board.flatten()[idx - win:idx + win])
    max_idx = np.floor_divide(tmp, board.shape[0]), tmp % board.shape[0]
    max_val = board[max_idx]
    return (max_val, max_idx)
#sample(idx=10,win=2)
#(2,3)

更新后OP提供了清晰:

def sample(board=None,x=1,y=1, wlen=1):
    # creating a dummy variable here. You don't need this for your code
    if board is None:
        board = np.array([[2.41791045, -1.70149254, -1.85074627, -1.46268657, ],
                          [-1.70149254, -1.91044776, -1.94029851, -1.85074627],
                          [-1.85074627, -1.94029851, -1.91044776, -1.70149254],
                          [-1.46268657, -1.85074627, -1.70149254, 2.41791045]])
    x1=x-wlen
    x2=x+wlen
    y1=y-wlen
    y2=y+wlen

    x1=max(x1,0)
    x2=min(x2,board.shape[0])
    y1=max(y1,0)
    y2=min(y2,board.shape[1])

    grid = board[x1:x2,y1:y2]
    xy = np.unravel_index(grid.argmin(),grid.shape)
    min_val = grid[xy]
    min_xy = (x - wlen + xy[0], y - wlen + xy[1])

    return min_val,min_xy

#sample(x=2,y=3,wlen=1)
#(-1.9402985100000001, (1, 2))

相关问题 更多 >