One-step multiples list generation?

E

Efrat Regev

Hello,

Suppose I have some non-numerical Foo and would like to create a list
of 20 Foo-s. Is there a one-step method (not a loop) of doing so? E.g.,
something like [Foo * 20] (which is obviously not the right way) that
would create [Foo, Foo, Foo, ...,Foo].
I tried looking through the docs, FAQs and help, but couldn't find
anything (the closest is range, but it seems it's only for numerics) - I
very much appreciate your time in answering. Also, please excuse me if I
used some wrong terminology.

Thanks,

Efrat
 
D

Damien Wyart

* Efrat Regev said:
Suppose I have some non-numerical Foo and would like to create a list
of 20 Foo-s. Is there a one-step method (not a loop) of doing so?

Maybe :

[ Foo ] * 20

or, more verbose,

[ Foo for _ in range(20) ]

?
 
R

Rocco Moretti

Damien said:
* Efrat Regev said:
Suppose I have some non-numerical Foo and would like to create a list
of 20 Foo-s. Is there a one-step method (not a loop) of doing so?


Maybe :

[ Foo ] * 20

or, more verbose,

[ Foo for _ in range(20) ]

If Foo is mutable, keep this in mind:
>>> a = [ [] ]*20 # A list of 20 empty lists
>>> print id(a[0]) == id(a[1]) True
>>> a[0].append(1)
>>> print a
[[1], [1], [1], [1], [1], [1], [1], [1], [1], [1], [1], [1], [1], [1],
[1], [1], [1], [1], [1], [1]]
>>>
>>> b = [ [] for _ in range(20) ] # A list of 20 empty lists
>>> print id(b[0]) == id(b[1]) False
>>> b[0].append(1)
>>> print b
[[1], [], [], [], [], [], [], [], [], [], [], [], [], [], [], [], [],
[], [], []]
 
R

Rocco Moretti

Rocco said:
Damien said:
* Efrat Regev said:
Suppose I have some non-numerical Foo and would like to create a list
of 20 Foo-s. Is there a one-step method (not a loop) of doing so?



Maybe :

[ Foo ] * 20

or, more verbose,

[ Foo for _ in range(20) ]

If Foo is mutable, keep this in mind:
a = [ [] ]*20 # A list of 20 empty lists
print id(a[0]) == id(a[1]) True
a[0].append(1)
print a
[[1], [1], [1], [1], [1], [1], [1], [1], [1], [1], [1], [1], [1], [1],
[1], [1], [1], [1], [1], [1]]
b = [ [] for _ in range(20) ] # A list of 20 empty lists
print id(b[0]) == id(b[1]) False
b[0].append(1)
print b
[[1], [], [], [], [], [], [], [], [], [], [], [], [], [], [], [], [],
[], [], []]

Oh, but also:
>>> Foo = []
>>> c = [ Foo for _ in range(20) ] # A list of 20 empty lists
>>> print id(c[0]) == id(c[1]) True
>>> c[0].append(1)
>>> print c
[[1], [1], [1], [1], [1], [1], [1], [1], [1], [1], [1], [1], [1], [1],
[1], [1], [1], [1], [1], [1]]

(The difference with the 'b' case is that a new list is created each
"time around", in the other cases, the same list is reused.
 
D

Damien Wyart

Thanks for these important and useful additions, they are very welcome !

In writing my answer I had immutables in mind, but mutables are a bit
more dangerous, here...
 
E

Efrat Regev

Damien said:
* Efrat Regev said:
Suppose I have some non-numerical Foo and would like to create a list
of 20 Foo-s. Is there a one-step method (not a loop) of doing so?


Maybe :

[ Foo ] * 20

or, more verbose,

[ Foo for _ in range(20) ]

?

Great. Thanks!
 
S

Steven D'Aprano

Thanks for these important and useful additions, they are very welcome !

In writing my answer I had immutables in mind, but mutables are a bit
more dangerous, here...

Mutables are easy to deal with using the copy module and list
comprehensions:
foo = []
import copy
multi_foo = [copy.copy(foo) for _ in range(10)]
multi_foo [[], [], [], [], [], [], [], [], [], []]
multi_foo[5].append(None)
multi_foo
[[], [], [], [], [], [None], [], [], [], []]

Or use copy.deepcopy if you need to.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,755
Messages
2,569,536
Members
45,020
Latest member
GenesisGai

Latest Threads

Top