Creating an array of sets in python

I am having problems with the list of sets, and I think that this is because I initialized it incorrectly, is this the right way to initialize and add 5000 sets to the list?

sets = [set()]*5000 i = 0 for each in f: line = each.split() if (some statement): i = line[1] else: sets[i].add(line[0]) 

any advice would be highly appreciated

+4
source share
2 answers

You keep a copy of the link to one set in each of your list indices. Thus, a change in one will also change the others.

To create a list of several sets, you can use list comprehension:

 sets = [set() for _ in xrange(5000)] 
+14
source

It works:

 >>> lotsosets=[set() for i in range(5)] >>> lotsosets [set([]), set([]), set([]), set([]), set([])] >>> lotsosets[0].add('see me?') >>> lotsosets [set(['see me?']), set([]), set([]), set([]), set([])] >>> lotsosets[1].add('imma here too') >>> lotsosets [set(['see me?']), set(['imma here too']), set([]), set([]), set([])] 

You should only use the form [x]*5000 if x is something immutable:

 >>> li=[None]*5 >>> li [None, None, None, None, None] >>> li[0]=0 >>> li [0, None, None, None, None] >>> li[1]=1 >>> li [0, 1, None, None, None] 

Or, if multiple references to a single element, such as an iterator, cause the desired behavior:

 >>> [iter('abc')]*3 [<iterator object at 0x100498410>, <iterator object at 0x100498410>, <iterator object at 0x100498410>] # 3 references to the SAME object 

Note the repeated link to the same iterator, which then creates the desired behavior using zip:

 >>> zip(*[iter('abcdef')]*3) [('a', 'b', 'c'), ('d', 'e', 'f')] 

Or a subset of a longer iterator:

 >>> [next(x) for x in [iter('abcdef')]*3] ['a', 'b', 'c'] 

While something like [list()]*5 probably does not create what is intended:

 >>> li=[list()]*5 >>> li [[], [], [], [], []] >>> li[0].append('whoa') >>> li [['whoa'], ['whoa'], ['whoa'], ['whoa'], ['whoa']] 
+3
source

Source: https://habr.com/ru/post/1491157/


All Articles