Ich möchte das Verständnis verschachtelter Listen verstehen. Unten habe ich einen Listenverständnisausdruck und deren for-Schleifenäquivalent aufgelistet.
Ich frage mich, ob mein Verständnis bei diesen richtig ist.
Zum Beispiel,
[(min([row[i] for row in rows]),max([row[i] for row in rows]))
for i in range(len(rows[0]))]
ist äquivalent zu
result=[]
for i in range(len(rows[0])):
innerResult=[]
for row in rows:
innerResult.append(row[i])
innerResult2=[]
for row in rows:
innerResult2.append(row[i])
tuple=(min(innerResult), max(innerResult2))
result.append(tuple)
Wenn ich verallgemeinern darf, denke ich
[exp2([exp1 for x in xSet]) for y in ySet]
Form kann wie folgt übersetzt werden. (Ich hoffe, ich habe Recht damit)
result=[]
for y in ySet:
innerResult =[]
for x in xSet:
innerResult.append(exp1)
exp2Result = exp2(innerResult)
result.append(exp2Result)
Für einen einfacheren Fall
[exp1 for x in xSet for y in ySet]
entspricht
result=[]
for x in xSet:
for y in ySet:
result.append(exp1)
wohingegen,
[[exp1 for x in xSet] for y in ySet]
entspricht
result=[]
for y in ySet:
innerResult=[]
for x in xSet:
innerResult.append(exp1)
result.append(innerResult)
Ich habe eine ähnliche Frage zu Äquivalent für Schleifenausdruck für komplexes Listenverständnis gestellt.
Die dort gegebenen Antworten rekonstruieren die Form, nachdem sie verstanden haben, was sie intern tut.
Ich möchte wissen, wie es systematisch funktioniert, damit ich das Konzept auf andere leicht unterschiedliche Beispiele anwenden kann.
quelle
cols = zip(*rows)
Sie einfachmin(col)
undmax(col)
für jede Spalte Folgendes verwendet hätten :[(min(c), max(c)) for c in cols]
. Oder in einer kurzen Zeile :[(min(c), max(c)) for col in zip(*rows)]
.Antworten:
Die kurze Antwort lautet: Ja, Sie haben Verständnis .
Es gibt nur einen Haken: Die Art und Weise, wie Sie normalerweise das Verständnis verschachtelter Listen in Python-Code verwenden, besteht darin, mehrdimensionale Arrays zu bearbeiten.
Ein typisches Beispiel ist, wenn Sie mit Matrizen arbeiten:
>>> matrix = [[1, 2, 3], [4, 5, 6], [7, 8, 9]] >>> [[el - 1 for el in row] for row in matrix] [[0, 1, 2], [3, 4, 5], [6, 7, 8]]
Wie Sie sehen können, funktioniert das "Verschachteln", indem jede Dimension der Matrix bearbeitet wird.
In den von Ihnen bereitgestellten Beispielen scheint es, dass
ySet
[übrigens ein unglücklicher Name, da Sets einer der mit Python bereitgestellten Typen sind] nur ein generischer Zähler ist, was es etwas schwieriger macht, zu verfolgen, was unter der Haube vor sich geht.Wie für Ihr erstes Beispiel:
>>> rows = ([1, 2, 3], [10, 20, 30]) >>> [(min([row[i] for row in rows]),max([row[i] for row in rows])) for i in range(len(rows[0]))] [(1, 10), (2, 20), (3, 30)]
Vielleicht möchten Sie sich die integrierte Funktion von zip ansehen :
>>> zip(rows[0], rows[1]) [(1, 10), (2, 20), (3, 30)]
oder für maximale Kürze und Eleganz:
>>> zip(*rows) [(1, 10), (2, 20), (3, 30)]
HTH!
quelle
In der Tat sind Sie richtig. Dies wird ausführlich im Abschnitt Ausdrücke in der Python-Sprachreferenz beschrieben .
Beachten Sie insbesondere die Reihenfolge der Verschachtelung mehrerer
for
s in einem einzigen Listenverständnis, das immer von links nach rechts erfolgt:>>> matrix = [[1, 2], [3, 4]] >>> [item for item in row for row in matrix] # oops! Traceback (most recent call last): File "<pyshell#1>", line 1, in <module> [item for item in row for row in matrix] NameError: name 'row' is not defined >>> [item for row in matrix for item in row] # nesting is in left-to-right order [1, 2, 3, 4]
quelle
[exp for item in row]
erstellt eine Liste mit einer bestimmten Zeile. Das "äußere" Listenverständnis erstellt eine Liste, in der jedes Element eine Liste ist, die von der "inneren" Listenkomposition erstellt wurde, eine für jede Zeile in der Matrix.