Python 根据索引公式更改数组的布尔值

Python 根据索引公式更改数组的布尔值,python,numpy,numpy-ndarray,Python,Numpy,Numpy Ndarray,我想创建一个64个组件的数组,显示所有的方块,其中一个空棋盘的两辆车可以从它们当前的位置移动。到目前为止,我是用for和while循环来完成的 我首先创建一个函数,以便更好地可视化电路板: import numpy as np def from_array_to_matrix(v): m=np.zeros((8,8)).astype('int') for row in range(8): for column in range(8): m

我想创建一个64个组件的数组,显示所有的方块,其中一个空棋盘的两辆车可以从它们当前的位置移动。到目前为止,我是用
for
while
循环来完成的

我首先创建一个函数,以便更好地可视化电路板:

import numpy as np
def from_array_to_matrix(v):
    m=np.zeros((8,8)).astype('int')
    for row in range(8):
        for column in range(8): 
            m[row,column]=v[row*8+column]
    return m

这里我将展示如何实际构建阵列:

# positions of the two rooks

a=np.zeros(64).astype('int')
a[15] = 1
a[25] = 1

print from_array_to_matrix(a)

# attack_a will be all the squares where they could move in the empty board
attack_a=np.zeros(64).astype('int')
for piece in np.where(a)[0]:
    j=0
    square=piece+j*8
    while square<64:
        attack_a[square]=1
        j+=1
        square=piece+j*8
    j=0
    square=piece-j*8
    while square>=0:
        attack_a[square]=1
        j+=1
        square=piece-j*8
    j=0
    square=piece+j
    while square<8*(1+piece//8):
        attack_a[square]=1
        j+=1
        square=piece+j
    j=0
    square=piece-j
    while square>=8*(piece//8):
        attack_a[square]=1
        j+=1
        square=piece-j

print attack_a
print from_array_to_matrix(attack_a)
#两辆车的位置
a=np.zeros(64.astype('int'))
a[15]=1
a[25]=1
从_数组_打印到_矩阵(a)
#攻击a将是他们可以在空棋盘中移动的所有方格
攻击类型('int')
对于np中的工件,其中(a)[0]:
j=0
正方形=件+j*8
当平方=0时:
攻击a[方格]=1
j+=1
正方形=件号j*8
j=0
正方形=件+j
方形=8*(件号//8):
攻击a[方格]=1
j+=1
正方形=件j
打印攻击
从数组打印到矩阵(攻击a)
有人建议我尽量避免使用
for
while
循环,只要有可能使用其他方法,因为它们往往很耗时。是否有任何方法可以在不使用
for
while
循环的情况下实现相同的结果?
也许可以使用这样一个事实,即我要为其赋值的索引可以由函数确定。

使用整形将一维数组转换为8x8二维矩阵,然后使用numpy advance indexing选择要设置为1的行和列:

import numpy as np
def from_array_to_matrix(v):
    return v.reshape(8,8)

# positions of the two rooks    
a=np.zeros(64).astype('int')
a[15] = 1
a[25] = 1

a = from_array_to_matrix(a)

# attack_a will be all the squares where they could move in the empty board
attack_a=np.zeros(64).astype('int')
attack_a = from_array_to_matrix(attack_a)

#these two lines replace your for and while loops
attack_a[np.where(a)[0],:] = 1
attack_a[:,np.where(a)[1]] = 1
输出:

a:

攻击a:

[[0 1 0 0 0 0 0 1]
 [1 1 1 1 1 1 1 1]
 [0 1 0 0 0 0 0 1]
 [1 1 1 1 1 1 1 1]
 [0 1 0 0 0 0 0 1]
 [0 1 0 0 0 0 0 1]
 [0 1 0 0 0 0 0 1]
 [0 1 0 0 0 0 0 1]]

有几种不同的方法可以做到这一点。当然,最简单的事情是使用矩阵


但您也可以对raveled阵列进行矢量化操作。例如,假设您在位置
0 Nice处有一辆车,您可以添加一个步骤,将解决方案重塑回一维向量吗?我需要最终结果是1-D,因为它在其他方面更实用。@3sm1r是的。只需使用
arr=arr.ravel()
展平(1-D)任何数组
arr
。请查看如何在网上接受答案,以便解决您的问题。谢谢你,泰。
重塑
ravel
操作是否耗时?在这种情况下,时间效率很重要,因为我需要做大量类似的操作。因此,也许我应该按照您的要求来处理raveled数组。@3sm1r。它们返回相同数据的视图,它们是否非常便宜,而且您无论如何只能执行一次
[[0 1 0 0 0 0 0 1]
 [1 1 1 1 1 1 1 1]
 [0 1 0 0 0 0 0 1]
 [1 1 1 1 1 1 1 1]
 [0 1 0 0 0 0 0 1]
 [0 1 0 0 0 0 0 1]
 [0 1 0 0 0 0 0 1]
 [0 1 0 0 0 0 0 1]]
array[8 * (n // 8):8 * (n // 8 + 1)] = True
array[n % 8::8] = True
matrix = array.reshape(8, 8)
array = martix.ravel()
array = matrix.reshape(-1)
matrix[m, :] = matrix[:, n] = True
m, n = np.nonzero(matrix)
matrix[m, :] = matrix[:, n] = True
n = np.nonzero(array)[0]
r = np.linspace(8 * (n // 8), 8 * (n // 8 + 1), 8, False).T.ravel()
c = np.linspace(n % 8, n  % 8 + 64, 8, False)
array[r] = array[c] = True