有没有快速的方法可以找到,如果连接了2D布尔区域上的两个点,你可以在一个值为True的正方形上向上,向下,向左和向右移动? 我们假设您将关注6x6 2D列表:
在代码中,那将是:
bool2DList = [6][6]
bool2DList = { True, True, False, False, True, True,
False, True, True, False, True, True,
False, True, True, False, False, True,
False, False, False, False, False, True,
False, False, False, False, True, True,
False, True, True, True, True, True }
绿色方块的值为True,蓝色的方式为False。我正在考虑函数(它可能需要递归),其中你将一个2D列表作为参数与一些元组的元组列表(坐标)和最后一个特殊点的元组,它可能有标题像这样:
def FindWay( bool2DList,listOfPoints,specialPointCoord )
在此示例中,特殊点将是坐标为5; 1的点P.让我们想象你会从那些特殊的点开始走路。没有踩到蓝色方块你能达到什么分?在这个例子中,只有点P4和P5(输出可以说是那些点的坐标,所以0; 5和5; 3)。它可能需要递归,但我不知道,身体应该是什么样子。
谢谢。
答案 0 :(得分:4)
我担心没有琐碎的方法可以做到这一点。这是一个图遍历问题,Python没有内置函数支持它。我希望您能够简单地实现breadth-first graph search。
非常简单地说,您保留了一个您已访问但未处理的节点列表;您已处理的另一个节点列表。步骤如下:
处理= [] 访问= [P] 访问时不是空的: 从访问列表中删除节点A. 对于每个节点B,您可以直接从A到达: 如果B是新的(不在访问或处理列表中): 将B放在访问列表中 把A放在处理清单上
这将找到您可以访问的所有节点。如果您担心特定节点,那么在循环内部,检查 B 是否是您的目标节点。当您将 B 放在访问列表中时,请将其放在前面,深度优先,背面为广度优先。
在此应用程序中,"您可以访问的所有节点"由具有相同布尔标签的边界组成。
答案 1 :(得分:0)
以下是一个如何编码的选项:
A = np.array([[0, 1, 1, 0], [1, 0, 1, 1], [1, 0, 1, 0], [0, 1, 0, 0]]).astype(bool)
print A
[[False True True False]
[ True False True True]
[ True False True False]
[False True False False]]
我们可以根据需要升级标准dfs功能:
def dfs_area(A, start):
graph = {}
res = np.zeros_like(A)
for index, x in np.ndenumerate(A):
graph[index] = x
visited, stack = set(), [start]
while stack:
vertex = stack.pop()
x, y = vertex[0], vertex[1]
if vertex not in visited and graph[vertex] == True:
visited.add(vertex)
if x < A.shape[0]-1:
stack.append((x+1, y))
if x > 1:
stack.append((x-1, y))
if y < A.shape[1]-1:
stack.append((x, y+1))
if y > 1:
stack.append((x, y-1))
res[tuple(np.array(list(visited)).T)] = 1
return res
假设我们想要连接到(1,2)的点 - 第二行,第三个值:
mask = dfs_area(A, (1,2))
>> mask
array([[0, 1, 1, 0],
[0, 0, 1, 1],
[0, 0, 1, 0],
[0, 0, 0, 0]])