Seite 1 von 1

Alle Elemente einer verschachtelten Liste in eine Liste

Verfasst: Sonntag 24. März 2013, 20:09
von matheblauwal
Was ich eigentlich will ist so etwas wie die Funktion "func":

Code: Alles auswählen

L = [1, 2, [3, 4, [5, 6, 7], 8]]
Li = func(L)
Li soll dann

Code: Alles auswählen

[1, 2, 3, 4, 5, 6, 7, 8]
sein.

Kennt jemand so eine Funktion oder hat eine Idee wie sie aussehen könnte?
Bei n-dimensionalen Listen kann man es über n verschachtelte for-Schleifen lösen, aber hier geht das nicht und auch nicht wenn man gar nicht weiß wie verschachtelt L ist.

Danke für alle Antworten.

PS: Falls es keine eingebaute Funktion gibt, bitte möglichst kurzer Code.

Re: Alle Elemente einer verschachtelten Liste in eine Liste

Verfasst: Sonntag 24. März 2013, 20:42
von BlackJack

Code: Alles auswählen

def flatten(iterable):
    try:
        for item in iterable:
            for subitem in flatten(item):
                yield subitem
    except TypeError:
        yield iterable


def main():
    L = [1, 2, [3, 4, [5, 6, 7], 8]]
    print list(flatten(L))


if __name__ == '__main__':
    main()

Re: Alle Elemente einer verschachtelten Liste in eine Liste

Verfasst: Sonntag 24. März 2013, 21:59
von derdon
Hier eine nicht-rekursive Version, die ich auf der Seite http://rightfootin.blogspot.de/2006/09/ ... atten.html gefunden habe:

Code: Alles auswählen

def flatten(l, ltypes=(list, tuple)):
    ltype = type(l)
    l = list(l)
    i = 0
    while i < len(l):
        while isinstance(l[i], ltypes):
            if not l[i]:
                l.pop(i)
                i -= 1
                break
            else:
                l[i:i + 1] = l[i]
        i += 1
    return ltype(l)
Vorteile gegenüber der rekursiven Version: Die Listen können beliebig tief verschachtelt sein, es wird niemals das Rekursionslimit erreicht. Ein Nachteil ist evtl. das dieser Code explizit auf Typen überprüft (hier per Default auf list und tuple), während der Code von BlackJack mit allen iterables funktioniert (und damit auch mit basestring-Objekten).

Re: Alle Elemente einer verschachtelten Liste in eine Liste

Verfasst: Sonntag 24. März 2013, 22:25
von mutetella
derdon hat geschrieben:Ein Nachteil ist evtl. das dieser Code explizit auf Typen überprüft (hier per Default auf list und tuple), während der Code von BlackJack mit allen iterables funktioniert (und damit auch mit basestring-Objekten).
Außer man überprüft nicht auf einzelne iterierbare types sondern benutzt stattdessen `collections.Iterable`:

Code: Alles auswählen

def nested2flat(*elements):
    for item in elements:
        if isinstance(item, collections.Iterable) and len(item) > 1:
            for inner_item in nested2flat(*item):
                yield inner_item
        else:
            yield item
Allerdings ist BlackJacks Lösung definitiv die "schönere"...

mutetella

Re: Alle Elemente einer verschachtelten Liste in eine Liste

Verfasst: Sonntag 24. März 2013, 22:32
von BlackJack
@mutetella: Nicht alles was iterierbar ist kann man mit diesem `isinstance()` testen und man kann ebenfalls nicht die Länge von allen iterierbaren Objekten ermitteln.

Re: Alle Elemente einer verschachtelten Liste in eine Liste

Verfasst: Sonntag 24. März 2013, 22:41
von mutetella
Ok... lasst es uns in den Müll kicken... :mrgreen:

Re: Alle Elemente einer verschachtelten Liste in eine Liste

Verfasst: Montag 25. März 2013, 14:53
von bords0
derdon hat geschrieben:Vorteile gegenüber der rekursiven Version: Die Listen können beliebig tief verschachtelt sein, es wird niemals das Rekursionslimit erreicht. Ein Nachteil ist evtl. das dieser Code explizit auf Typen überprüft (hier per Default auf list und tuple), während der Code von BlackJack mit allen iterables funktioniert (und damit auch mit basestring-Objekten).
Außer, dass der Code von BlackJack eben nicht mit strings funktioniert.

Re: Alle Elemente einer verschachtelten Liste in eine Liste

Verfasst: Montag 25. März 2013, 14:59
von BlackJack
Den notwendigen Test auf `basestring` kann man aber sehr einfach einbauen.

Re: Alle Elemente einer verschachtelten Liste in eine Liste

Verfasst: Montag 25. März 2013, 21:21
von derdon
bords0 hat geschrieben:
derdon hat geschrieben:Vorteile gegenüber der rekursiven Version: Die Listen können beliebig tief verschachtelt sein, es wird niemals das Rekursionslimit erreicht. Ein Nachteil ist evtl. das dieser Code explizit auf Typen überprüft (hier per Default auf list und tuple), während der Code von BlackJack mit allen iterables funktioniert (und damit auch mit basestring-Objekten).
Außer, dass der Code von BlackJack eben nicht mit strings funktioniert.
Doch, er funktioniert mit Strings. Nur eben nicht so, wie du es erwartest ;) Wie Unterklassen von list und wie tuple behandelt werden sollen, ist doch auch reine Definitionssache.

Re: Alle Elemente einer verschachtelten Liste in eine Liste

Verfasst: Montag 25. März 2013, 21:30
von Sirius3
@derdon: nein! Die Elemente eines Strings sind wieder Strings (halt mit nur einem Zeichen), die wiederum iterierbar sind, was eine „endlose“ Rekursion zur Folge hat.

Re: Alle Elemente einer verschachtelten Liste in eine Liste

Verfasst: Montag 25. März 2013, 21:43
von BlackJack
@derdon: Es dürfte mit Zeichenketten *nicht* funktionieren. Zeichenketten sind iterierbar. Die Elemente sind einzelne Zeichen — in Form einer Zeichenkette. Also iterierbar. Die Elemente sind einzelne Zeichen — in Form einer Zeichenkette. Also iterierbar. Die Elemente sind einzelne Zeichen — in Form einer Zeichenkette. Also iterierbar. Die Elemente sind einzelne Zeichen — in Form einer Zeichenkette. Also iterierbar… ;-)

Edit: Verdammt. Zu lange mit dem absenden gewartet. :-)

Re: Alle Elemente einer verschachtelten Liste in eine Liste

Verfasst: Montag 25. März 2013, 21:47
von Sirius3
@Blackjack: aber der versuch eine endlose Iteration in einem Fließtext unterzubringen gibt 10 Bonusminuten. :)

Re: Alle Elemente einer verschachtelten Liste in eine Liste

Verfasst: Dienstag 26. März 2013, 00:29
von derdon
Das kommt davon, wenn man über Code redet, den man selber nicht getestet hat :oops:

Re: Alle Elemente einer verschachtelten Liste in eine Liste

Verfasst: Montag 8. April 2013, 19:19
von matheblauwal
Hey, danke für alle eure Antworten! :D
Ich denke ich werde den Code von derdon benutzen, weil es bei einer solch verschachtelten Liste auch Listenelemente geben kann die Strings sind.