0

everyone. I'm writing a simple function in Python 2.7 using the Networkx 1.9 Module for testing that my graph partitioning algorithm implementation works correctly. To that end, I have a list, dvecs, which has a list for each block in the partition of lists which give information about the edges from each node to the classes in the partition. Take a gander:

#dvecs : list of len(P) lists which correspond to a list of degree vectors of each block
    numBlocks = len(P)
    dvecs = [[]] * numBlocks

    for block in P:
        blockNo = P.index(block)
        dvecs[blockNo] = [[-1] * numBlocks] * len(block)
        for node in block:
            nodeNo = block.index(node)
            for otherBlock in P:
                otherBlockNo = P.index(otherBlock)
                dvecs[blockNo][nodeNo][otherBlockNo] = len(set(nx.neighbors(G,  node)).intersection(set(otherBlock)))

The problem I'm having is that in the last line of the nested loop, the line that starts with dvec[blockNo...], according to the debugger, each of the entries in the middle-depth list(the one with indices specified by nodeNo) are being updated with the same value for each iteration of the innermost loop. In other words, it is as if 'node' is being held constant and nodeNo is iterated through all nodes in the block. What is going on here?

In response to Roman, I tried the following:

for blockNo, block in enumerate(P):
        dvecs[blockNo] = [[-1] * numBlocks] * len(block)
        for nodeNo, node in enumerate(block):
            for otherBlockNo, otherBlock in enumerate(P):
                dvecs[blockNo][nodeNo][otherBlockNo] = len(set(nx.neighbors(G, node)).intersection(set(otherBlock)))

I am, however, getting the same behavior. Did I miss something?

Robert G
  • 1
  • 1
  • note use enumerate instead of getting index of ex:http://stackoverflow.com/questions/1185545/python-loop-counter-in-a-for-loop – Roman A. Taycher Jul 25 '14 at 04:34
  • Thanks, Roman, for the quick response. I'm very new to python so I haven't even heard of that until now. – Robert G Jul 25 '14 at 04:35
  • If you're new you might also want to read about with statements for cleaning up files/other resources: http://stackoverflow.com/questions/3012488/what-is-the-python-with-statement-designed-for – Roman A. Taycher Jul 25 '14 at 04:47
  • Cool, thanks. Not sure if it notifies you about edits to my initial posts(I'm new to SO as well), but I tried using enumerate but I'm getting the same issue. Can you take a look at the code I posted? – Robert G Jul 25 '14 at 04:57

1 Answers1

1

This:

[[]] * n

gives you a list containing the same empty list, n times. So appending to any one of them appends to "all" of them — there's only one nested list.

Try this, which will create n distinct empty lists:

[[] for _ in range(n)]
Eevee
  • 47,412
  • 11
  • 95
  • 127
  • Thanks for the tip. I change this but I'm getting the same issue. – Robert G Jul 25 '14 at 05:34
  • you have to make the same fix inside the first loop, where you assign to `dvecs[blockNo]`. probably easier would be to just use `.append([])` instead of building lists full of junk values ahead of time – Eevee Jul 25 '14 at 05:43