Поиск единой стоимости (TypeError: объект 'Graph' не подлежит подписке)

Я реализую функцию Uniform Cost Search в python, но когда я пытаюсь запустить свой код, появляется сообщение об ошибке "TypeError: объект 'Graph' не подлежит подписке". Вот мой код ниже. Я импортировал очередь и график в свою основную функцию. Я занимался этим некоторое время, но не смог найти проблему, может ли кто-нибудь помочь с этим? Благодаря:

from graph import Graph
from queue import PriorityQueue

def uniform_cost_search(graph, start_node, goal_node):
  queue=PriorityQueue()
  queue.insert([start_node],0)
  while not queue.is_empty():
      node=queue.remove()
      current=node[1][len(node[1])-1]
      if goal_node in node[1]:
          print("Path found:"+str(node[1])+",Cost="+str(node[0]))
          break

      cost=node[0]
      for i in graph[current]:# This line is causing the error
        temp=node[1][:]
        temp.append(i)
        queue.insert(temp,cost+graph[current][i])


if __name__ == "__main__":

  # Defining Graph
  graph = Graph()

  # setting up nodes and neighbours
  graph.edges = {
    'A': set(['B', 'D']),
    'B': set(['A','E','C']),
    'C': set(['B', 'E', 'G']),
    'D': set(['A','E','F']),
    'E': set(['B', 'C', 'D', 'G']),
    'F': set(['D','G']),
    'G': set(['F','E','C'])
  }

 # setting up connection costs
 graph.weights = {
    'AB': 5, 'AD': 3,
    'BA': 5, 'BE': 4, 'BC': 1,
    'CB': 1, 'CE': 6, 'CG': 8,
    'DA': 3, 'DE': 2, 'DF': 2,
    'EB': 4, 'EC': 6, 'ED': 2, 'EG': 4,
    'FD': 2, 'FG': 3,
    'GF': 3, 'GE': 4, 'GC': 8
 }

uniform_cost_search(graph, 'A', 'G')
"""
the above statement should result in the following:

Shortest Path: A,D,F,G
Cost: 8
"""

Код для графика:

class Graph:

def __init__(self):
    self.edges = {} # dictionary of edges NODE: NEIGHBOURS
    self.weights = {} # dictionary of NODES and their COSTS

def neighbours(self, node):
    """
    The function returns the neighbour of the node passed to it,
    which is essentially the value of the key in the edges dictionary.
    :params node: (string) a node in the graph
    :return: (list) neighbouring nodes
    """

    return self.edges[node]

def get_cost(self, from_node, to_node):
    """
    Gets the cost of a connection between adjacent nodes.
    :params from_node: (string) starting node
    :params to_node: (string) ending node
    :return: (int) 
    """
    
    return self.weights[(from_node + to_node)]



if __name__ == "__main__":
# testing out the graph class
graph = Graph()

# setting up nodes and neighbours
graph.edges = {
    'A': set(['B', 'D']),
    'B': set(['A','E','C']),
    'C': set(['B', 'E', 'G']),
    'D': set(['A','E','F']),
    'E': set(['B', 'C', 'D', 'G']),
    'F': set(['D','G']),
    'G': set(['F','E','C'])
}

# setting up connection costs
graph.weights = {
    'AB': 5, 'AD': 3,
    'BA': 5, 'BE': 4, 'BC': 1,
    'CB': 1, 'CE': 6, 'CG': 8,
    'DA': 3, 'DE': 2, 'DF': 2,
    'EB': 4, 'EC': 6, 'ED': 2, 'EG': 4,
    'FD': 2, 'FG': 3,
    'GF': 3, 'GE': 4, 'GC': 8
}

print("Neighbours of Node A are:",graph.neighbours('A'))
print("Cost going from A to D is:", graph.get_cost('A','D'))

Код очереди:

import heapq

class PriorityQueue:

def __init__(self):
    self.__queue = []
    self.__index = 0

def insert(self, item, priority):
    """
    The function takes in the item and its priority, wraps it up in a tuple and 
    inserts it in the heap.
    :params item: item to be inserted into the queue
    :params priority: the priority of the item to be inserted
    :return: None
    """

    heapq.heappush(self.__queue, (priority, self.__index, item))
    self.__index += 1

def remove(self):
    """
    The functions removes the lowest priority item from the priority queue (via heaps)
    and returns the item along with the cost of it.
    :return : the item with the lowest priority
    """

    temp = heapq.heappop(self.__queue)
    
    cost = temp[0]
    item = temp[-1]

    return cost, item

def is_empty(self):
    """
    Checks whether the queue is empty or not.
    :returns: (Boolean)
    """
    return len(self.__queue) == 0

if __name__ == "__main__":

# testing priority queue


queue = PriorityQueue()
queue.insert('e', 9)
queue.insert('a', 2)
queue.insert('h', 13)
queue.insert('c', 11)
print(queue.remove())
print(queue.remove())
print(queue.remove())

1 ответ

Чтобы иметь подписку, тип объекта должен либо наследоваться от другого типа, который может быть подписан (например, dict), либо реализовывать специальный метод __getitem__().

Graph не делает ни того, ни другого, поэтому это не индексируемый тип объекта.

Другие вопросы по тегам