Station - Ein Code-Erzeuger für strukturierte MyKa-Programme
Aufgabe des Code-Erzeugers
Der Code-Erzeuger hat die Aufgabe, (strukturierte) MyKa-Programme in (strukturierte) MyKaGoto-Programme zu übersetzen. Die Arbeitsweise des Code-Erzeugers soll am folgenden Beispiel-Programm verdeutlicht werden.
Aus einer strukturierten Darstellung des MyKa-Programms
links while nichtVorWand: ziegelHinlegen schritt #while
soll eine strukturierte Darstellung des folgenden MyKaGoto-Programms erzeugt werden:
links label .L0 if nichtVorWand: goto .L1 else: goto .L2 label .L1 ziegelHinlegen schritt goto .L0 label .L2
Der Code-Erzeuger verarbeitet als Quellcode also eine Listen-Darstellung des MyKa-Programms.
[
['links'],
['while',
['nichtVorWand'],
[
['ziegelHinlegen'],
['schritt']
]
]
]
Diesen Quellcode transformiert der Code-Erzeuger in ein strukturiertes MyKaGoto-Programm.
[
(None, ['links']),
('.L0', ['noop']),
(None, ['if', ['nichtVorWand'], ['goto', '.L1'], ['goto', '.L2']]),
('.L1', ['noop']),
(None, ['ziegelHinlegen']),
(None, ['schritt']),
(None, ['goto', '.L0']),
('.L2', ['noop'])
]
Implementierung des Code-Erzeugers
Der Code-Erzeuger wird durch ein Objekt der Klasse UebersetzerWhileList realisiert.
Dieses Objekt verfügt insbesondere über eine Methode uebersetzen, die
letztlich für die Erzeugung des Zielcodes zuständig ist.
class UebersetzerMyKaList(object):
def __init__(self):
self.quellcode = None
def setQuellcode(self, q):
self.quellcode = q
def uebersetzen(self):
def c_programm(p):
'programm : anweisungsfolge'
return c_anweisungsfolge(p)
def c_anweisungsfolge(p):
'''anweisungsfolge : anweisung anweisungsfolge
| anweisung'''
if len(p) > 1:
return c_anweisung(p[0]) + c_anweisungsfolge(p[1:])
else:
return c_anweisung(p[0])
def c_anweisung(p):
'''anweisung : ELANW
| PASS
| WHILE bedingung DP anweisungsfolge ENDWH
| IF bedingung DP anweisungsfolge ELSE DP anweisungsfolge ENDIF'''
if p[0] in ["schritt",
"links",
"rechts",
"ziegelHinlegen",
"ziegelAufheben",
"markeSetzen",
"markeLoeschen",
"pass"]:
return [(None, p)]
elif p[0] == 'while':
ergebnis_true = c_anweisungsfolge(p[2])
ergebnis_wh = [('.L' + str(self.zaehler), ['noop']), \
(None, ['if', p[1], ['goto', '.L' + str(self.zaehler+1)], \
['goto', '.L' + str(self.zaehler+2)]]), \
('.L' + str(self.zaehler+1), ['noop'])] + \
ergebnis_true + \
[(None, ['goto', '.L' + str(self.zaehler)]), \
('.L' + str(self.zaehler+2), ['noop'])]
self.zaehler = self.zaehler + 3
return ergebnis_wh
elif p[0] == 'if':
ergebnis_true = c_anweisungsfolge(p[2])
ergebnis_false = c_anweisungsfolge(p[3])
ergebnis_if = [(None, ['if', p[1], ['goto', '.L' + str(self.zaehler)], \
['goto', '.L' + str(self.zaehler+1)]]), \
('.L' + str(self.zaehler), ['noop'])] + \
ergebnis_true + \
[(None, ['goto', '.L' + str(self.zaehler+2)])] + \
[('.L' + str(self.zaehler+1), ['noop'])]+ \
ergebnis_false + \
[('.L' + str(self.zaehler+2), ['noop'])]
self.zaehler = self.zaehler + 3
return ergebnis_if
self.zaehler = 0
if self.quellcode != []:
return c_programm(self.quellcode)
else:
return [(0, "p")]
Ein Objekt der Klasse UebersetzerMyKaList kann also benutzt werden, um strukturierte
While-Programme in strukturierte Goto-Programme zu übersetzen.
from uebersetzerMyKaList import *
# Testprogramm
quellcode = [
['links'],
['while',
['nichtVorWand'],
[
['ziegelHinlegen'],
['schritt']
]
]
]
codeerzeuger = UebersetzerMyKaList()
# Erzeugung des Zielcodes
codeerzeuger.setQuellcode(quellcode)
zielcode = codeerzeuger.uebersetzen()
# Ausführung des Programms und Ausgabe der Zustände
print('Quellcode:')
print()
for zeile in quellcode:
print(zeile)
print()
print('Zielcode:')
print()
for zeile in zielcode:
print(zeile)
Aufgabe 1
Probiere das selbst einmal aus. Teste verschiedene strukturierte MyKa-Programme.