Tutorial
对Networkx做初步了解
https://networkx.org/documentation/stable/tutorial.html的笔记
创建一个图
import networkx as nx
G = nx.Graph()
创建了一个空图,没有节点和边。根据定义,图是由一组节点和它们之间的边构成。在Networkx中,节点可以是任何可哈希(hashable)的对象,例如,文本字符串、图像、XML对象、另一个图、自定义节点对象等。
节点
一次添加一个节点
G.add_node(1)
通过可迭代容器,例如列表添加节点
G.add_nodes_from([2, 3])
添加带有属性的节点,(node, node_attribute_dict)
G.add_nodes_from([
(4, {"color": "red"}),
(5, {"color": "green"}),
])
一个图的节点合并到另一个图中:
H = nx.path_graph(10)
G.add_nodes_from(H)
一个图把另一个图当做节点:
G.add_node(H)
边
一次加入一个边
G.add_edge(1, 2)
e = (2, 3)
G.add_edge(*e) # unpack edge tuple*
通过列表加入多个边
G.add_edges_from([(1, 2), (1, 3)])
一个边元组可以是节点的二维元组,也可以是包含节点属性的三维元组,例如(2, 3, {‘weight’: 3.1415})
G.add_edges_from(H.edges)
清除所有的边和节点
G.clear()
下面是一个例子
G.add_edges_from([(1, 2), (1, 3)])
G.add_node(1)
G.add_edge(1, 2)
G.add_node("spam") # adds node "spam"
G.add_nodes_from("spam") # adds 4 nodes: 's', 'p', 'a', 'm'
G.add_edge(3, 'm')
可以得到8个节点,3条边的图
G.number_of_nodes()
8
G.number_of_edges()
3
邻接关系报告的顺序(例如,G.adj、G.successors、G.predecessors)与边添加的顺序相同。然而,G.edges 的顺序是包括节点顺序和每个节点的邻接关系在内的邻接关系的顺序。请参见下面的示例:
DG = nx.DiGraph()
DG.add_edge(2, 1) # adds the nodes in order 2, 1
DG.add_edge(1, 3)
DG.add_edge(2, 4)
DG.add_edge(1, 2)
assert list(DG.successors(2)) == [1, 4]
assert list(DG.edges) == [(2, 1), (2, 4), (1, 3), (1, 2)]
查看图中元素
G.nodes、G.edges、G.adj 和 G.degree。它们是节点、边、邻居(邻接关系)以及图中节点的度
可以用.items()、.data() 等方法进行数据属性的迭代
list(G.nodes)
[1, 2, 3, 'spam', 's', 'p', 'a', 'm']
list(G.edges)
[(1, 2), (1, 3), (3, 'm')]
list(G.adj[1]) # or list(G.neighbors(1))
[2, 3]
G.degree[1] # the number of edges incident to 1
2
可以指定全部节点的子集报告边和度
G.edges([2, 'm'])
EdgeDataView([(2, 1), ('m', 3)])
G.degree([2, 3])
DegreeView({2: 1, 3: 2})
删除图中元素
Graph.remove_node(), Graph.remove_nodes_from(), Graph.remove_edge() and Graph.remove_edges_from()
G.remove_node(2)
G.remove_nodes_from("spam")
list(G.nodes)
[1, 3, 'spam']
G.remove_edge(1, 3)
使用图的构造器
G.add_edge(1, 2)
H = nx.DiGraph(G) # create a DiGraph using the connections from G
list(H.edges())
[(1, 2), (2, 1)]
edgelist = [(0, 1), (1, 2), (2, 3)]
H = nx.Graph(edgelist) # create a graph from an edge list
list(H.edges())
[(0, 1), (1, 2), (2, 3)]
adjacency_dict = {0: (1, 2), 1: (0, 2), 2: (0, 1)}
H = nx.Graph(adjacency_dict) # create a Graph dict mapping nodes to nbrs
list(H.edges())
[(0, 1), (0, 2), (1, 2)]
获取边和节点
除了使用 Graph.edges, 和 Graph.adj,也可以使用下标
G = nx.Graph([(1, 2, {"color": "yellow"})])
G[1] # same as G.adj[1]
AtlasView({2: {'color': 'yellow'}})
G[1][2]
{'color': 'yellow'}
G.edges[1, 2]
{'color': 'yellow'}
也可以获取边的属性
G.add_edge(1, 3)
G[1][3]['color'] = "blue"
G.edges[1, 2]['color'] = "red"
G.edges[1, 2]
{'color': 'red'}
得到所有的边可以使用G.adjacency(), or G.adj.items(),注意对于无向图,邻接迭代可以得到每个边两次
FG = nx.Graph()
FG.add_weighted_edges_from([(1, 2, 0.125), (1, 3, 0.75), (2, 4, 1.2), (3, 4, 0.375)])
for n, nbrs in FG.adj.items():
for nbr, eattr in nbrs.items():
wt = eattr['weight']
if wt < 0.5: print(f"({n}, {nbr}, {wt:.3})")
(1, 2, 0.125)
(2, 1, 0.125)
(3, 4, 0.375)
(4, 3, 0.375)
可以用下面的方法修正
for (u, v, wt) in FG.edges.data('weight'):
if wt < 0.5:
print(f"({u}, {v}, {wt:.3})")
(1, 2, 0.125)
(3, 4, 0.375)
给图、节点、边添加属性
G = nx.Graph(day="Friday")
G.graph
{'day': 'Friday'}
G.graph['day'] = "Monday"
G.graph
{'day': 'Monday'}
G.add_node(1, time='5pm')
G.add_nodes_from([3], time='2pm')
G.nodes[1]
{'time': '5pm'}
G.nodes[1]['room'] = 714
G.nodes.data()
NodeDataView({1: {'time': '5pm', 'room': 714}, 3: {'time': '2pm'}})
G.add_edge(1, 2, weight=4.7 )
G.add_edges_from([(3, 4), (4, 5)], color='red')
G.add_edges_from([(1, 2, {'color': 'blue'}), (2, 3, {'weight': 8})])
G[1][2]['weight'] = 4.7
G.edges[3, 4]['weight'] = 4.2
有向图
DG = nx.DiGraph()
DG.add_weighted_edges_from([(1, 2, 0.5), (3, 1, 0.75)])
DG.out_degree(1, weight='weight')
0.5
DG.degree(1, weight='weight')
1.25
list(DG.successors(1))
[2]
list(DG.neighbors(1))
[2]
多边图
MG = nx.MultiGraph()
MG.add_weighted_edges_from([(1, 2, 0.5), (1, 2, 0.75), (2, 3, 0.5)])
dict(MG.degree(weight='weight'))
{1: 1.25, 2: 1.75, 3: 0.5}
GG = nx.Graph()
for n, nbrs in MG.adjacency():
for nbr, edict in nbrs.items():
minvalue = min([d['weight'] for d in edict.values()])
GG.add_edge(n, nbr, weight = minvalue)
nx.shortest_path(GG, 1, 3)
[1, 2, 3]