2013-03-29 17 views
7

Właściwie staram się połączyć dwie listy do jednej strunie, ale zachować je uporządkowane oznacza:Łącząc dwie listy ciąg

list1 = [1,2,3,4,5] 
list2 = ["one", "two", "three", "four", "five"] 

result = "1one2two3three4four5five" 

(wykazy zawsze mają taką samą długość, lecz różnią się zawartością)

Na chwila robię to w ten sposób:

result = "" 
i = 0 

for entry in list1: 
    result += entry + list2[i] 
    i += 1 

myślę, że musi być bardziej pythonic sposobem, aby to zrobić, ale nie wiem właściwie.

Ktoś z was może mi pomóc w tej sprawie.

Odpowiedz

10
list1 = [1,2,3,4,5] 
list2 = ["one", "two", "three", "four", "five"] 

print ''.join([str(a) + b for a,b in zip(list1,list2)]) 
 
1one2two3three4four5five 
+0

To jest [wyrażenie generujące] (http://www.youtube.com/watch?v=pShL9DCSIUw) używane razem z ['str.join()'] (http://docs.python.org/3.3 /library/stdtypes.html#str.join). –

+0

Uczyń to ze zrozumieniem listy, a będzie jeszcze szybciej. Podając '.join() 'wyrażenie generatora, Python musi utworzyć z niego listę * tak * ponieważ' .join() 'musi przeskanować dane wejściowe dwukrotnie, raz, aby obliczyć całkowitą długość wyjścia i raz, aby wygenerować wynik. "[Zrozumienie listy]" jest szybsze niż 'lista (wyrażenie generujące)'. –

+0

@MartijnPieters Prawda, ale prostota jest prawdopodobnie ważniejsza – jamylak

2
>>> ''.join(str(n)+s for (n,s) in zip(list1, list2)) 
'1one2two3three4four5five' 

tutaj:

  • for (n,s) in zip(list1, list2) iteruje par pierwiastków w list1 i list2 (tj 1 i "one" etc);
  • str(n)+s przekształca każdą parę w ciąg znaków (np. "1one");
  • ''.join(...) łączy wyniki w jeden ciąg.
2
>>> import itertools 
>>> ''.join(map(str, itertools.chain.from_iterable(zip(list1, list2)))) 
1one2two3three4four5five' 

Objaśnienie:

  • zip(list1, list2) tworzy listę zawierającą krotki pasujące elementy z dwóch list:

    >>> zip(list1, list2) 
    [(1, 'one'), (2, 'two'), (3, 'three'), (4, 'four'), (5, 'five')] 
    
  • itertools.chain.from_iterable() spłaszcza że zagnieżdżonej listy:

    >>> list(chain.from_iterable(zip(list1, list2))) 
    [1, 'one', 2, 'two', 3, 'three', 4, 'four', 5, 'five'] 
    
  • Teraz musimy upewnić się, że istnieje tylko struny, więc stosujemy str() do wszystkich elementów za pomocą map()

  • Ostatecznie ''.join(...) łączy elementy listy w jeden ciąg bez separatora.
+0

Twierdzę, że jest to najbardziej elastyczna, pythonic odpowiedź. Zaletą jest to, że można z radością dodać więcej iterables do 'zip()' i to by działało idealnie, inne odpowiedzi wymagałyby zmiany w zależności od liczby iterables. –

+1

@Lattyware elastyczne, tak, ale zdecydowanie przesadzone dla tej konkretnej sytuacji – jamylak

+2

@ Lattyware: dla mnie odpowiedź Ashwini jest najbardziej pythonic - "proste jest lepsze niż złożone", wiesz. – georg

2

Korzystanie string formatting z str.join() i zip():

>>> list1 = [1,2,3,4,5] 
>>> list2 = ["one", "two", "three", "four", "five"] 

>>> "".join("{0}{1}".format(x,y) for x,y in zip(list1,list2)) 
'1one2two3three4four5five' 

zip(list1,list2) powraca coś takiego: [(1, 'one'), (2, 'two'), (3, 'three'), (4, 'four'), (5, 'five')].

Teraz dla każdej pozycji z tej listy stosujemy formatowanie ciągów znaków, a następnie łączymy całe wyrażenie generatora za pomocą str.join().

+0

lub po prostu "{} {}". Format (* p) dla p w ... ' – georg

+0

@ thg435 W ten sposób jest jaśniejszy – jamylak

+0

@jamylak: Nie jestem wielkim fanem formatu, więc osobiście użyj '"% d% s "% p dla p ...'. – georg