给定坐标列表,将值添加到这些坐标,直到最短路径发生变化

Given a list of coordinates, add values to those coordinates until shortest path changes

所以我几天前提出了一个问题(这里是 ) basically what I'm trying to do is given a 3D array, and a list of coordinates, add values to those coordinates until shortest path changes, the user Mohammed Kashif 帮我解决了我的问题,但那是一个二维坐标列表,现在我想做的是做同样的事情但是使用 3D 坐标列表,第一个坐标列表与前 5 个数组和第二个坐标列表与接下来的 5 个数组。这就是我尝试的: (这只是一个例子,我的坐标列表,3D数组可以有更多的元素)

import numpy as np
import networkx as nx
from copy import deepcopy

arr = np.array ([[[  0., 303.,  43.,  26.,  20.],
                  [  0.,   0.,   0.,   0.,   0.],
                  [  0.,  21.,   0.,   8.,   0.],
                  [  0.,  47.,   5.,   0.,   4.],
                  [  0.,  35.,   0.,   1.,   0.]],

                 [[  0., 356.,  40.,  32.,  49.],
                  [  0.,   0.,   0.,   0.,   0.],
                  [  0.,  36.,   0.,   1.,   0.],
                  [  0.,  25.,   1.,   0.,   1.],
                  [  0.,  40.,   0.,   3.,   0.]],

                 [[  0., 372.,  27.,  34.,  44.],
                  [  0.,   0.,   0.,   0.,   0.],
                  [  0.,  37.,   0.,   3.,   0.],
                  [  0.,  41.,   8.,   0.,   1.],
                  [  0.,  34.,   0.,   6.,   0.]],

                 [[  0., 300.,  46.,  37.,  46.],
                  [  0.,   0.,   0.,   0.,   0.],
                  [  0.,  40.,   0.,   1.,   0.],
                  [  0.,  48.,   2.,   0.,   5.],
                  [  0.,  43.,   0.,   2.,   0.]],

                 [[  0., 321.,  42.,  22.,  22.],
                  [  0.,   0.,   0.,   0.,   0.],
                  [  0.,  42.,   0.,   3.,   0.],
                  [  0.,  20.,   3.,   0.,   5.],
                  [  0.,  20.,   0.,   9.,   0.]],

                 [[  0., 319.,  48.,  21.,  39.],
                  [  0.,   0.,   0.,   0.,   0.],
                  [  0.,  29.,   0.,   0.,   1.],
                  [  0.,  38.,   0.,   0.,   7.],
                  [  0.,  40.,   1.,   5.,   0.]],

                 [[  0., 374.,  46.,  25.,  28.],
                  [  0.,   0.,   0.,   0.,   0.],
                  [  0.,  25.,   0.,   0.,   2.],
                  [  0.,  44.,   0.,   0.,   6.],
                  [  0.,  44.,   2.,   9.,   0.]],

                 [[  0., 341.,  34.,  21.,  49.],
                  [  0.,   0.,   0.,   0.,   0.],
                  [  0.,  27.,   0.,   0.,   9.],
                  [  0.,  25.,   0.,   0.,   8.],
                  [  0.,  49.,   1.,   1.,   0.]],

                 [[  0., 310.,  30.,  44.,  47.],
                  [  0.,   0.,   0.,   0.,   0.],
                  [  0.,  34.,   0.,   0.,   2.],
                  [  0.,  21.,   0.,   0.,   8.],
                  [  0.,  37.,   9.,   8.,   0.]],

                 [[  0., 321.,  27.,  44.,  31.],
                  [  0.,   0.,   0.,   0.,   0.],
                  [  0.,  21.,   0.,   0.,   5.],
                  [  0.,  41.,   0.,   0.,   1.],
                  [  0.,  41.,   1.,   5.,   0.]]])

n = 5          #Number of array for each path list and coordinates list 
graphs = []
pathaux = []

for i in arr:
    graphs.append(nx.from_numpy_array(i, create_using = nx.DiGraph)) #Create graphs from numpy array

for graph in graphs:
    pathaux.append(nx.shortest_path(graph, 0, 1, weight = 'weight'))   #Find the shortest path

path = [pathaux[i: i+n] for i in range(0, len(pathaux), n)] #Creates a 3D list "separating" for each 5 arrays 

print(path)
#path = [[[0, 4, 3, 2, 1], [0, 3, 1], [0, 2, 1], [0, 3, 2, 1], [0, 3, 1]], [[0, 3, 4, 2, 1], [0, 4, 2, 1], [0, 3, 1], [0, 2, 4, 3, 1], [0, 2, 1]]]

#path[0] = [[0, 4, 3, 2, 1], [0, 3, 1], [0, 2, 1], [0, 3, 2, 1], [0, 3, 1]] #Shortest path for the first 5 arrays
#path[1] = [[0, 3, 4, 2, 1], [0, 4, 2, 1], [0, 3, 1], [0, 2, 4, 3, 1], [0, 2, 1]] #Shortest path for the next 5 arrays

#Here are the 3D list of coordinates, the first two pair is for the first 5 array, the next four pairs are for the other 5 arrays
coordinates = [[[4, 3], [3, 2]], [[3, 4], [4, 2], [2, 4], [4, 3]]]

for i in coordinates:
    for x,y in i:
        # Make deepcopies of path and arr
        # For the first iteration, set newpath = path
        new_path = deepcopy(pathaux)
        temp_arr = deepcopy(arr)

        # Set counter for each coordinate to zero
        cnt = 0

        # Iterate till a change in path is observed
        while pathaux == new_path:
            # Add 1 to x,y
            temp_arr[:, x, y] = temp_arr[:, x, y] + 1

            # Increment the counter
            cnt += 1

            # Reconstruct the graph and shortest path
            temp_graph = []
            new_path = []
            for i in temp_arr:
                temp_graph.append(nx.from_numpy_array(i, create_using = nx.DiGraph))
                
            for graph in temp_graph:
                new_path.append(nx.shortest_path(graph, 0, 1, weight = 'weight'))

        #If we are out of the loop, this means that
        # the shortest path has changed. Print the details.
        print("For coordinates X={} and Y={} the change is at {}".format(x, y, cnt))

这是这段代码的输出

#For the first 5 arrays
For coordinates X=4 and Y=3 the change is at 3
For coordinates X=3 and Y=2 the change is at 1

#For the next 5 arrays
For coordinates X=3 and Y=4 the change is at 1
For coordinates X=4 and Y=2 the change is at 1
For coordinates X=2 and Y=4 the change is at 1
For coordinates X=4 and Y=3 the change is at 3

如您所见,坐标是正确的,但更改的值是错误的,如果我手动执行,将值添加到坐标直到我的列表更改这是我的真实输出:

#For the first 5 arrays
For coordinates X=4 and Y=3 the change is at 5
For coordinates X=3 and Y=2 the change is at 6

#For the next 5 arrays
For coordinates X=3 and Y=4 the change is at 1
For coordinates X=4 and Y=2 the change is at 1
For coordinates X=2 and Y=4 the change is at 3
For coordinates X=4 and Y=3 the change is at 3

我考虑过将 arr 从 3D 数组重塑为形状为 (2, 5, 5, 5) 的 4D 数组,但我相信我必须做一个双 for-loop 所以它更慢,我知道这是一个很长的问题,但我不知道如何使具有第一个最短路径和第一个坐标列表的相应前 5 个数组一起工作,并为接下来的五个具有相应最短路径和坐标的数组做同样的事情。再次抱歉,问题很长,如有任何帮助,我们将不胜感激,谢谢!

你应该单独考虑分区。对现有代码应用以下更改,它应该可以工作:

...

arr_partition = [arr[i: i+n] for i in range(0, len(arr), n)]
j = 0
for i in coordinates:
    print("The tree is", j)
    for x, y in i:
        new_path = deepcopy(path[j])
        temp_arr = deepcopy(arr_partition[j])
        cnt = 0
        while path[j] == new_path:
            ...
    print()
    j += 1
        
...

输出:

The tree is 0
For coordinates X=4 and Y=3 the change is at 5
For coordinates X=3 and Y=2 the change is at 6

The tree is 1
For coordinates X=3 and Y=4 the change is at 1
For coordinates X=4 and Y=2 the change is at 1
For coordinates X=2 and Y=4 the change is at 3
For coordinates X=4 and Y=3 the change is at 3