Gegeben ist eine kontextfreie Grammatik G und ein Wort w. Es stellt sich die Frage, ob w zu L(G) gehört, ob also die von G erzeugte Sprache das Wort w enthält. Um dies zu entscheiden, wird aus der kontextfreien Grammatik G ein nichtdeterministischer Stackautomat N konstruiert. Der Automat wird so konstruiert, dass er genau alle jene Wörter akzeptiert, die zu L(G) gehören.
Satz: Zu jeder kontextfreien Grammatik G gibt es einen nichtdeterministischen Stackautomaten N, der die von G erzeugte Sprache L(G) erkennt.
Zum Beweis des Satzes konstruieren wir aus einer beliebig gegebenen kontextfreien Grammatik G einen (erweiterten) nichtdeterministischen Stackautomaten, der die von G erzeugte Sprache durch leeren Stack erkennt.
Wir erweitern die Definition des nichtdeterministischen Stackautomaten in der Weise, dass wir die Übergangsrelation definieren als
d ⊆ Z × E? × H? × H* × Z.
Hierbei ist Z die Zustandsmenge, E das Eingabealphabet und E? = E ∪ {ε}, H das Stackalphabet und H? = H ∪ {ε}.
Die neue Übergangsrelation kann also in einem Schritt eine ganzes Wort w von Stackzeichen auf dem Stack ablegen. Dies geschieht so, dass dieses Wort zeichenweise, mit dem letzten Zeichen zuerst, in den Stack geschrieben wird. Das erste Zeichen von w erscheint als oberstes Stackzeichen.
Offenbar sind der normale Stackautomat und der erweiterte Stackautomat äquivalente Maschinen, denn einerseits ist der normale Stackautomat ein Spezialfall des erweiterten Stackautomaten, andererseits lässt sich jeder erweiterte Stackautomat in ein normalen Stackautomaten umformen, indem ein erweiterter Zustandsübergang in eine Folge von normalen Zustandsübergängen zerlegt wird, wobei zusätzliche Zustände eingeführt werden.
So wird jeder erweiterte Zustandsübergang
s | a | h | w | t |
mit w = w0 ... wn-1, n > 1 ersetzt durch die normalen Zustandsübergänge
s | a | h | wn-1 | tn-1 |
tn-1 | ε | ε | wn-2 | tn-2 |
... | ||||
t2 | ε | ε | w1 | t1 |
t1 | ε | ε | w0 | t |
wobei t1, ..., tn-1 als neue Zustände eingeführt werden.
Wir konstruieren aus der Grammatik G = (V, T, P, S) einen erweiterten nichtdeterministischen Stackautomaten N = (Z, E, H, d, q, F) mit
Z = {q, r}
E = T
H = V ∪ T
Die Übergangsrelation d enthält Tupel (s, a, h, h', s') bestehend aus dem aktuellem Zustand s, dem gelesenen Eingabezeichen a, dem vom Stack entfernten Stackzeichen h, dem auf dem Stack neu abgelegten Wort h' und dem neuen Zustand s'.
Die Übergangsrelation wird wie folgt konstruiert. Zunächst wird ein Tupel
q | ε | ε | S | r |
eingeführt. Wenn der Stackautomat zu arbeiten beginnt, legt er also zuerst das Startsymbol S der Grammatik auf den Stack und geht in den Zustand r über. Der Zustand r ist der einzige Zustand außer dem Startzustand q; der Stackautomat benötigt keine weiteren Zustände.
Dann wird für jede Produktion
Xu
der Grammatik ein entsprechendes Tupel zur Übergangsrelation d hinzugefügt, und zwar
r | ε | X | u | r |
Wenn der Stackautomat also die linke Seite X einer Produktion auf dem Stack vorfindet, ersetzt er sie nichtdeterministisch durch eine zugehörige rechte Seite u.
Ferner wird für jedes Terminalzeichen a ∈ T ein Tupel
r | a | a | ε | r |
eingeführt.
Wenn der Stackautomat also das Zeichen a liest und er gleichzeitig das Zeichen a auf dem Stack vorfindet, entfernt er es vom Stack.
Die Arbeitsweise des so konstruierten Stackautomaten bildet genau den Ersetzungsmechanismus der Grammatik nach. Daher erkennt der Stackautomat genau die von der Grammatik erzeugte Sprache.
Beispiel: Gegeben sei die Grammatik G = (V, T, P, S) mit T = {a, b} und den Produktionen
S | ![]() | aY | aSY |
Y | ![]() | b |
Die Grammatik erzeugt die Sprache { anbn | n ∈ ℕ }.
Der erweiterte Stackautomat hat die Zustände q = 0 und r = 1 und enthält folgende Zustandsübergänge (s, a, h, h', s'):
Wenn der Stackautomat beispielsweise das Wort aabb abarbeitet, schreibt er zunächst das Startsymbol S in den Stack. Er findet dann S im Stack vor und ersetzt S durch aSY, ohne ein Zeichen der Eingabe zu lesen. Nun befindet sich a als oberstes Zeichen auf dem Stack. Der Stackautomat liest a und entfernt a vom Stack. Nun ist S das oberste Zeichen auf dem Stack. Ohne ein Zeichen zu lesen, ersetzt der Stackautomat diesmal S durch aY. Der Stackinhalt ist jetzt aYY und a ist das oberste Zeichen. Wieder liest der Stackautomat ein a und entfernt a vom Stack. Anschließend ersetzt er Y durch b, liest b und entfernt b, ersetzt das verbleibende Y durch b und liest b und entfernt b. Nun ist die Eingabe vollständig abgearbeitet und der Stack ist leer. Somit akzeptiert der Stackautomat das Wort aabb durch leeren Stack.
Weiter: [CYK-Algorithmus] oder [up]