2010-03-15 12 views

Odpowiedz

12
>>> a = [1, 2, 3] 
>>> b = [] 
>>> for i in a: 
    b.extend([i, i]) 


>>> b 
[1, 1, 2, 2, 3, 3] 

lub

>>> [a[i//2] for i in range(len(a)*2)] 
[1, 1, 2, 2, 3, 3] 
+0

Powinieneś użyć '//' do podziału piętra również w Pythonie 2. –

+0

@Mike: masz rację, z wyjątkiem oczywiście w '/' division zapewnia powrót 'int'. – SilentGhost

38
>>> a = range(10) 
>>> [val for val in a for _ in (0, 1)] 
[0, 0, 1, 1, 2, 2, 3, 3, 4, 4, 5, 5, 6, 6, 7, 7, 8, 8, 9, 9] 

nb _ jest tradycyjnie używany jako nazwa zmiennej zastępczej, w której nie chcesz nic robić z zawartością zmiennej. W tym przypadku służy tylko do generowania dwóch wartości za każdym razem wokół zewnętrznej pętli.

Aby przekształcić tę listę z listy w generator, zamień nawiasy kwadratowe na nawiasy okrągłe.

+1

'_' jest obecnie używany do i18n/l10n (google). Nadal go używam * jeśli * Wiem, że w tym module nie będzie i18n. Inaczej ja (chciałbym) użyć '__' (dwa podkreślenia). –

1

użyłbym

import itertools 
foo = [1, 5, 3, 6] 
new = itertools.chain.from_iterable([item, item] for item in foo) 

new będzie iterator że lazily iteracje nad powielonych elementów. Jeśli potrzebujesz rzeczywistej wyliczonej listy, możesz wykonać list(new) lub skorzystać z jednego z innych rozwiązań.

+1

lub krótszy: 'itertools.chain.from_iterable (itertools.izip (foo, foo))' –

+0

Rozważyłem ten kod, który jest krótszy, ale nie wydawał mi się jaśniejszy. –

6

Jeśli masz już roundrobin receptury opisane w dokumentacji dla itertools-i to jest bardzo przydatny, to możesz po prostu użyć

roundrobin(my_list, my_list) 
+0

+1, jest to dobry sposób, aby to osiągnąć. –

1

Na ile Guido lubi operatorów funkcjonalne, mogą być dość cholernie przydatny:

>>> from operator import add 
>>> a = range(10) 
>>> b = reduce(add, [(x,x) for x in a]) 
+0

W przypadku zmniejszenia, przydatne często oznacza zadziwiająco wolne. Ważne jest mierzenie tego, co robi 'redu". Często szokujące jest to, jak bardzo obliczenia zmniejszają siły. –

+0

Zrobiłem skrypt testowy za pomocą każdej z metod na tej stronie z baselist = range (10) i 1 000 000 iteracji. Najwolniej zajęło 5,094 sekundy, a najszybsze 3,622 sekundy. Mój przykład redukcji trwał 3.906 sekund. –

+1

'zakres (10)' jest mały, więc złożoność płaci niewielką rolę. To rozwiązanie jest kwadratowe; wszystkie inne, które tu widzę, są liniowe. Także niektóre inne wydają mi się bardziej czytelne. –

8

użyłbym zip i itertools.chain.

>>> import itertools 
>>> l = [1,5,3,6,16] 
>>> list(itertools.chain(*zip(l,l))) 
[1, 1, 5, 5, 3, 3, 6, 6, 16, 16] 

Uwaga: ja tylko używane list spożywać generator, aby go dopasować do drukowania. Prawdopodobnie nie potrzebujesz połączenia list w swoim kodzie ...

1

Możliwe jest użycie mnożenia listy. Sprawa, której potrzebujesz każdemu członkowi listy razem, wystarczy użyć posortowanej metody.

>>> lst = [1,2,3,4] 
>>> sorted(lst*2) 
[1,1,2,2,3,3,4,4] 
+0

Co się stanie, jeśli chcesz zachować kolejność oryginalnej listy? A co się stanie, jeśli pozycje na liście nie będą podlegały reglamentacji? – Moberg

Powiązane problemy