1

I want to draw a bipartite graph connecting colleagues and moviepreferences. How can I show in the graph both the node name (so the moviename or colleague name) and the node attribute (whether it is a colleague or a movie) in the nodes ?

My current code only displays the node attribute and drops the node name.

My code:

BG = nx.Graph()
BG.add_nodes_from(employees, bipartite=0, _type='employee')
BG.add_nodes_from(movies, bipartite=1, _type='movie')
edgeinfo = pd.read_csv('Employee_Movie_Choices.txt', sep='\t')
edges = [tuple(x) for x in edgeinfo.values]
BG.add_edges_from(edges)

labels = dict((n,d['_type']) for n,d in BG.nodes(data=True))

%matplotlib notebook
import matplotlib.pyplot as plt

plt.figure()
pos = nx.spring_layout(BG)
edges = BG.edges()
nx.draw_networkx(BG, pos, edges=edges, labels=labels)

If I create label tuples, he gives me an error:

BG = nx.Graph()
BG.add_nodes_from(employees, bipartite=0, _type='employee')
BG.add_nodes_from(movies, bipartite=1, _type='movie')
edgeinfo = pd.read_csv('Employee_Movie_Choices.txt', sep='\t')
edges = [tuple(x) for x in edgeinfo.values]
BG.add_edges_from(edges)

labels = dict((n,d['_type']) for n,d in BG.nodes(data=True))  ###ik krijg hier naam movie en employee niet meer bij !!!
labels_new = [(k, v) for k, v in labels.items()]
#labels = [tuple(n,d['_type']) for n, d in BG.nodes(data=True)]
#nx.draw(BG, labels=labels)

%matplotlib notebook
import matplotlib.pyplot as plt

plt.figure()
pos = nx.spring_layout(BG)
edges = BG.edges()
nx.draw_networkx(BG, pos, edges=edges, labels=labels_new)

Error: ---> nx.draw_networkx(BG, pos, edges=edges, labels=labels_new) AttributeError: 'list' object has no attribute 'items'

1 Answer 1

1

Why error arises

From the documentation of draw_networkx , labels needs to be a dictionary while labels_new you fed is a list.

labels (dictionary, optional (default=None)) – Node labels in a dictionary keyed by node of text labels

From your code,

labels_new=[(k, v) for k, v in labels.items()]

Thus, the error AttributeError: 'list' object has no attribute 'items' arises.

Workaround: customize the labels dictionary

I do not have the data, but a quick hack can be

labels = dict((n, "(" + n + "," + d['_type'] + ")") for n,d in BG.nodes(data=True))

Demo

import networkx as nx
from networkx.algorithms import bipartite
%matplotlib notebook
import matplotlib.pyplot as plt

BG = nx.Graph()
employees = [str(i) for i in range(3)]
movies = ["mA", "mB", "mC"]
BG.add_nodes_from(employees, bipartite=0, _type='emp')
BG.add_nodes_from(movies, bipartite=1, _type='mov')
edges = [("0", "mA"), ("0", "mC"), ("1", "mA"),("1", "mB"), ("2", "mA")]
BG.add_edges_from(edges)
labels = dict((n, "(" + n + "," + d['_type'] + ")") for n,d in BG.nodes(data=True))

# Setting up pos for drawing bipartite graph. See the reference for more info
X, Y = bipartite.sets(BG)
pos = dict()
pos.update( (n, (1, i)) for i, n in enumerate(X) ) # put nodes from X at x=1
pos.update( (n, (2, i)) for i, n in enumerate(Y) ) # put nodes from Y at x=2

plt.figure()
edges = BG.edges()
nx.draw_networkx(BG, pos, edges=edges, labels=labels)

enter image description here

Reference

mdml's answer for drawing bipartite graph

Sign up to request clarification or add additional context in comments.

1 Comment

This worked ! Thank you very much for helping me out !

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.