使用networkx与我自己的对象
我有自己的对象,比如说“意大利香肠”。我有一份关于每个意大利香肠之间连接的边的列表,还有一份意大利香肠的列表。然后我用networkx这个库来构建一个图。我想找出从一个意大利香肠到另一个意大利香肠的最短路径的权重。但是,我遇到了一个错误,错误信息显示了networkx内部的一些内容,如下:
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "pizza.py", line 437, in shortestPath
cost = nx.shortest_path_length(a, spepp, tpepp, True)
File "/Library/Python/2.6/site-packages/networkx-1.3-py2.6.egg/networkx/algorithms/shortest_paths/generic.py", line 181, in shortest_path_length
paths=nx.dijkstra_path_length(G,source,target)
File "/Library/Python/2.6/site-packages/networkx-1.3-py2.6.egg/networkx/algorithms/shortest_paths/weighted.py", line 119, in dijkstra_path_length
(length,path)=single_source_dijkstra(G,source, weight = weight)
File "/Library/Python/2.6/site-packages/networkx-1.3-py2.6.egg/networkx/algorithms/shortest_paths/weighted.py", line 424, in single_source_dijkstra
edata=iter(G[v].items())
File "/Library/Python/2.6/site-packages/networkx-1.3-py2.6.egg/networkx/classes/graph.py", line 323, in __getitem__
return self.adj[n]
KeyError: <pizza.pepperoni object at 0x100ea2810>
有没有人知道这个错误是什么,或者我需要在我的披萨类中添加什么,才能不出现这个KeyError错误?
补充说明:我的边的格式是正确的。不过我不确定这些对象是否可以作为节点来处理。
1 个回答
3
如果你有边和节点分别以列表的形式存在,那么在 networkx 中构建图形是非常简单的。考虑到你在构建图形对象时遇到的问题,最好的办法是一步一步地检查在 networkx 中构建图形的过程:
import networkx as NX
import string
import random
G = NX.Graph() # initialize the graph
# just generate some synthetic data for the nodes and edges:
my_nodes = [ ch for ch in string.ascii_uppercase ]
my_nodes2 = list(my_nodes)
random.shuffle(my_nodes2)
my_edges = [ t for t in zip(my_nodes, my_nodes2) if not t[0]==t[1] ]
# now add the edges and nodes to the networkx graph object:
G.add_nodes_from(my_nodes)
G.add_edges_from(my_edges)
# look at the graph's properties:
In [87]: len(G.nodes())
Out[87]: 26
In [88]: len(G.edges())
Out[88]: 25
In [89]: G.edges()[:5]
Out[89]: [('A', 'O'), ('A', 'W'), ('C', 'U'), ('C', 'F'), ('B', 'L')]
# likewise, shortest path calculation is straightforward
In [86]: NX.shortest_path(G, source='A', target='D', weighted=False)
Out[86]: ['A', 'W', 'R', 'D']
根据我的经验,Networkx 的接口非常宽松,特别是它会接受各种类型的对象作为节点和边。节点可以是任何可哈希的对象,除了 None。
我能想到的可能导致你提到的错误的原因是,或许在你创建图形后,你 直接 修改了图形对象(也就是 dict, *G*),这是不应该做的——有很多方法可以安全地访问和操作图形。