Verarbeitung von arithmetischen Ausdrücken, die spaltenweise statt zeilenweise organisiert sind.
- Teil 1: Spaltenweise Addition oder Multiplikation
- Teil 2: Spaltenweise Ausdrücke mit Operatoren-Priorisierung
Mehrere Zeilen mit Zahlen und Operatoren, die spaltenweise gelesen werden müssen.
Beispiel:
1 2 3 +
4 5 6 *
Spaltenweise gelesen:
- Spalte 1:
['1', '4']→ Zahl oder Rechnung - Spalte 2:
['2', '5']→ Zahl oder Rechnung - Spalte 3:
['3', '6']→ Zahl oder Rechnung - Spalte 4:
['+', '*']→ Operatoren
for rechnung in list(zip(*[zeile.split() for zeile in aufgabe.zeilen])):
*operanden, operator = rechnung
aufgabe.loesung1 += sum(map(int, operanden)) if operator == "+" else prod(map(int, operanden))Schritt für Schritt:
-
Zeilen aufteilen:
[zeile.split() for zeile in aufgabe.zeilen]
- Jede Zeile wird an Leerzeichen gesplittet
- Ergebnis: Liste von Listen
- Beispiel:
[['1', '2', '3', '+'], ['4', '5', '6', '*']]
-
Transponieren (Zeilen → Spalten):
zip(*[...])
*unpacked die Listezip()gruppiert Element-Position-weise- Beispiel:
[('1', '4'), ('2', '5'), ('3', '6'), ('+', '*')]
-
Operanden und Operator trennen:
*operanden, operator = rechnung
- Letztes Element:
operator - Alle vorherigen:
operanden(als Liste) - Beispiel:
rechnung = ('1', '4', '+')→operanden = ['1', '4'],operator = '+'
- Letztes Element:
-
Berechnung:
sum(map(int, operanden)) if operator == "+" else prod(map(int, operanden))
- Addition (
+): Summiere alle Operanden - Multiplikation (
*): Multipliziere alle Operanden prod()vonmathModul: Produkt aller Elemente
- Addition (
Beispiel:
Eingabe:
1 2 +
3 4 +
Spalten:
('1', '3', '+') → 1 + 3 = 4
('2', '4', '+') → 2 + 4 = 6
Lösung1 = 4 + 6 = 10
faktoren = []
for spalte in list(zip_longest(*[zeile for zeile in aufgabe.zeilen]))[:-1]:
if all(zeichen == ' ' for zeichen in spalte):
continue
*operanden, operator = spalte
operand = int(''.join(operand for operand in operanden))
if operator in ("+", "*"):
aufgabe.loesung2 += prod(faktoren)
faktoren = []
befehl = "addiere" if operator == "+" else "multipliziere"
if befehl == "addiere":
aufgabe.loesung2 += operand
else:
faktoren.append(operand)
aufgabe.loesung2 += prod(faktoren)Unterschiede zu Teil 1:
-
zip_longeststattzip:zip_longest(*[zeile for zeile in aufgabe.zeilen])
- Behält alle Spalten, auch wenn Zeilen unterschiedlich lang sind
- Füllt kürzere Zeilen mit
Noneauf - Wichtig: Zeilen werden nicht gesplittet (zeichenweise!)
-
Letzte Spalte ignorieren:
[...][:-1]
- Vermutlich Padding oder Separator
-
Leerzeichen-Spalten überspringen:
if all(zeichen == ' ' for zeichen in spalte): continue
- Spalten mit nur Leerzeichen werden ignoriert
-
Operanden zu Zahl zusammenfügen:
operand = int(''.join(operand for operand in operanden))
- Mehrere Zeichen werden zu einer Zahl kombiniert
- Beispiel:
['1', '2', '3']→"123"→123
-
Operator als Modus-Wechsel:
if operator in ("+", "*"): aufgabe.loesung2 += prod(faktoren) faktoren = [] befehl = "addiere" if operator == "+" else "multipliziere"
+oder*sind Befehle, nicht unmittelbare Operationen- Setzen den Modus für folgende Operanden
- Vor Modus-Wechsel: Produkt der gesammelten Faktoren addieren
-
Zwei Modi:
Modus "addiere":
if befehl == "addiere": aufgabe.loesung2 += operand
- Operand wird direkt zur Lösung addiert
Modus "multipliziere":
else: faktoren.append(operand)
- Operand wird zu Faktoren-Liste hinzugefügt
- Produkt wird erst bei nächstem Operator-Wechsel berechnet
-
Abschluss:
aufgabe.loesung2 += prod(faktoren)
- Nach allen Spalten: Verbleibende Faktoren multiplizieren und addieren
Beispiel:
Eingabe (zeichenweise):
1 + 2 3 *
↓ ↓ ↓ ↓ ↓
Spalte 1: ('1',) → Operator fehlt → benutze vorherigen Modus
Spalte 2: ('+',) → Modus = "addiere"
Spalte 3: ('2',) → addiere: 0 + 2 = 2
Spalte 4: ('3',) → addiere: 2 + 3 = 5
Spalte 5: ('*',) → Modus = "multipliziere"
Teil 1:
- Zeit: O(n * m) wobei n = Anzahl Zeilen, m = Anzahl Spalten
zip()und Iteration durch alle Spalten
- Platz: O(n * m) für transponierte Datenstruktur
Teil 2:
- Zeit: O(n * m)
zip_longest()und Iteration durch alle Spalten- String-Join und Int-Konvertierung pro Spalte
- Platz: O(n * m + k) wobei k = Anzahl Faktoren in Liste
Transposition mit zip():
zip(*liste)ist die idiomatische Python-Methode für Matrix-Transposition- Beispiel:
zip(*[[1,2], [3,4]])→[(1,3), (2,4)]
zip vs. zip_longest:
zip(): Stoppt bei kürzester Sequenzzip_longest(): Geht bis zur längsten Sequenz, füllt mitNoneauf
Unpacking mit *variable:
*operanden, operator = listepackt alle außer letztes Element- Python 3 Feature für flexible Zuweisungen
prod() Funktion:
- Seit Python 3.8 in
mathModul - Äquivalent zu
sum()für Multiplikation prod([])= 1 (neutrales Element der Multiplikation)
Operator als Modus:
- Operatoren sind nicht Befehle für vorherige Operanden
- Sondern Modus-Setter für folgende Operanden
- Wichtig für Verständnis der Teil 2 Logik
Zeichenweise vs. Token-weise:
- Teil 1: Token-weise (
split()) - Teil 2: Zeichenweise (kein
split()) - Erklärt warum
operand = int(''.join(...))nötig ist