user1317221_G
user1317221_G

Reputation: 15441

explanation for networkx code python

I am new to coding python. I am hoping to modify this code to develop a bipartite two mode version. It is code from networkx used to make a geometrci random graph. I have got to grips with most of this function but I am having trouble understanding exactly what lines 94 to 99 are doing. I understand while, zip and nodes.pop() but other parts are confusing for a newbie. Can anyone help with an explanation for what this part of the code is doing more than the general # description given ?

G=nx.Graph()
G.name="Random Geometric Graph"
G.add_nodes_from(range(n)) 
if pos is None:
    # random positions
    for n in G:
        G.node[n]['pos']=[random.random() for i in range(0,dim)]
else:
    nx.set_node_attributes(G,'pos',pos) 
# connect nodes within "radius" of each other
# n^2 algorithm, could use a k-d tree implementation
nodes = G.nodes(data=True)
while nodes:             #line94
    u,du = nodes.pop()
    pu = du['pos']
    for v,dv in nodes:
        pv = dv['pos']
        d = sum(((a-b)**2 for a,b in zip(pu,pv))) #line99
        if d <= radius**2:
            G.add_edge(u,v)
return G

Upvotes: 1

Views: 587

Answers (1)

Niklas B.
Niklas B.

Reputation: 95298

nodes = [some list]
while nodes:
  a = nodes.pop()
  for b in nodes:
    # do something

This piece of code is a quite frequently seen idiom to combine every node with every other node exactly once (so the order of a and b shouldn't matter for the operation performed in the # do something part).

It works because the empty list is considered a falsy value in the condition of the while loop, while non-empty lists are considered boolean true.

d = sum(((a-b)**2 for a,b in zip(pu,pv)))

This line computes the square of the Euclidean distance of the two vectors pu and pv. This is best demonstrated by taking it apart:

>>> pu = (6,6,6)
>>> pv = (1,3,7)
>>> zip(pu, pv)
[(6, 1), (6, 3), (6, 7)]
>>> [(a-b) for a,b in zip(pu, pv)]
[5, 3, -1]
>>> [(a-b)**2 for a,b in zip(pu, pv)]
[25, 9, 1]
>>> sum((a-b)**2 for a,b in zip(pu, pv))
35

In the last step, we don't use a list comprehension any more, because we don't need a list. sum just needs the values in some iterable form, so we use a generator expression instead.

Upvotes: 2

Related Questions