简体   繁体   中英

Networkx: Replacing labels of nodes

I have the following minimal code:

import networkx as nx
import matplotlib.pyplot as plt

G = nx.DiGraph()
#G = nx.Graph()
#G = nx.path_graph(4)

pos1 = {0: (0, 0), 1: (2, 1), 2: (2, 0), 3: (2,-1)}
G.add_edge(0, 1)
G.add_edge(0, 3)
G.add_edge(1, 2)
G.add_edge(2, 3)

# First Network
plt.figure(0)
nx.draw_networkx(G, pos1) # Puts numbers as labels of nodes
plt.axis("off")
plt.savefig('graph1.png')

# Second network 
plt.figure(1)
mapping = {0: "Zero", 1: "One", 2: "Two", 3: "Three"}
H = nx.relabel_nodes(G, mapping)
nx.draw_networkx(H)  # Works

''' The below line I want to modify '''
#nx.draw_networkx(H, pos1) # Doesn't work  
                          # Says: NetworkXError: Node 'Zero' has no position 

plt.axis("off")
plt.savefig('graph2.png')
plt.show() 

Here I am trying to replace the label names in the new graph H . But it shows an error since I am using coordinates for the nodes.

Right now the outputs are:

图1

图2

The second graph needs to be corrected. Also, can the sizes of the nodes be auto-adjusted and even-odd numbered (labels for the first.network) nodes be colored differently?

PS. If networkx has limitations, then an example with some other module may also serve the purpose.

The simplest approach would be to create a relabelled pos dictionary using the new node names:

pos1 = {0: (0, 0), 1: (2, 1), 2: (2, 0), 3: (2,-1)}
mapping = {0: "Zero", 1: "One", 2: "Two", 3: "Three"}
pos_new = {mapping[k]: v for k, v in pos1.items()}
# use the above with nx.draw_networkx(H, pos_new)

I think the best way to solve this is to not use the nx.draw.networkx command but rather the separate draw commands for labels, nodes and edges. With nx.draw.networkx_labels you can pass your dictionary directly without changing your nodes names:

import networkx as nx
import matplotlib.pyplot as plt

G = nx.DiGraph()

pos1 = {0: (0, 0), 1: (2, 1), 2: (2, 0), 3: (2,-1)}
G.add_edge(0, 1)
G.add_edge(0, 3)
G.add_edge(1, 2)
G.add_edge(2, 3)

node_colors = ['red'if i%2==0 else 'blue' for i in G.nodes]
mapping = {0: "Zero", 1: "One", 2: "Two", 3: "Three"}

plt.figure()

nx.draw_networkx_nodes(G, pos=pos1,node_color=node_colors, node_size=500)
nx.draw_networkx_edges(G, pos=pos1)
nx.draw_networkx_labels(G, pos=pos1, labels=mapping)

plt.axis("off")
plt.show() 

This produces:

在此处输入图像描述

If you want to fit the node sizes to the labels, manipulate them. If you only care about the text, not about the node itself. Don't use the nx.draw.networkx_nodes command, instead add the bbox argument to nx.draw.networkx_labels . Like so:

plt.figure()

#nx.draw_networkx_nodes(G, pos=pos1,node_color=node_colors, node_size=500)
nx.draw_networkx_edges(G, pos=pos1)
nx.draw_networkx_labels(G, pos=pos1, labels=mapping, bbox ={})

plt.axis("off")
plt.show() 

Which produces:

在此处输入图像描述

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM