Lewy rekurencji - Left recursion
W formalnego języka teorii z informatyki , po lewej rekursji jest szczególnym przypadkiem rekursji gdzie ciąg jest rozpoznawany jako część języka przez fakt, że rozkłada się na sznurku od tego samego języka (po lewej) i przyrostka (na prawo). Na przykład, może być uznane jako suma ponieważ może być podzielony na również sumę i , odpowiednie rozszerzenie.
W zakresie kontekstu wolne gramatyki , A nieterminalowi do lewej rekurencyjne, że od lewej symboli w jednym z jego produkcji, jest sama w sobie (w przypadku lewego bezpośredniego rekursji) lub można się o około sekwencji podstawień (w przypadku pośrednich lewej rekursji).
Definicja
Gramatyka jest lewy rekurencyjny wtedy i tylko wtedy, gdy istnieje nieterminalowi symbol , który może czerpać do zdań postaci z siebie jak skrajnej lewej symbolem. Symbolicznie,
- ,
gdzie wskazuje operację wytwarzania jednego lub więcej podstawień, a to dowolna sekwencja symbol terminalny.
Bezpośredni lewej rekursji
Bezpośredni lewej rekursji występuje, gdy definicja może być spełniony tylko jeden zastąpienia. Wymaga ona regułę formularza
gdzie to sekwencja nieterminali i zaciskami. Na przykład, zasada
jest bezpośrednio po lewej rekurencyjne. W lewej do prawej rekurencyjne zejście parser dla tej reguły może wyglądać
void Expression() {
Expression();
match('+');
Term();
}
i taki kod spadnie do nieskończonej rekursji, gdy wykonywane.
Pośrednie lewej rekursji
Pośrednie lewej rekursji występuje, gdy definicja lewej rekursji jest spełniony poprzez kilka zastępstw. To pociąga za sobą zestaw reguł następujący wzór
w których to sekwencje, z których każda może wydzielały łańcuch pusty , natomiast mogą być dowolne sekwencje symbol terminalny wcale. Zauważ, że te sekwencje mogą być puste. wyprowadzenie
następnie podaje jako od lewej w jego ostatecznej postaci zdań.
Usuwanie lewej rekursji
Lewy rekurencji często stwarza problemy dla analizatorów, albo dlatego, że prowadzi je do nieskończonej rekurencji (jak w przypadku większości top-down parserami ) lub dlatego, że oczekują zasady w normalnej formie, która zabrania (jak w przypadku wielu oddolnych parser , włącznie z algorytmem cyk ). Dlatego gramatyka jest często wstępnie przetworzone w celu wyeliminowania lewy rekursji.
Usuwanie lewy bezpośredniej rekursji
Ogólny algorytm do usunięcia lewej bezpośredni rekurencji następująco. Liczne udoskonalenia tej metody zostały dokonane. Na lewo-rekurencyjne nieterminalowi , odrzucić wszelkie zasady formie i za te, które pozostają:
gdzie:
- każdy jest sekwencją niepusty z nieterminali i terminali oraz
- każdy jest sekwencją nieterminali i terminali, które nie rozpoczyna się .
Zastąpić te dwa zestawy, jeden zestaw produkcjach dla :
oraz innego zestawu do świeżej nieterminalowi (często nazywana „ogon” lub „reszta”):
Powtórz ten proces, dopóki nie bezpośrednich lewą szczątków rekursji.
Jako przykład rozważmy zestaw reguł
Może to być przepisywane w celu uniknięcia lewej rekursji jako
Usuwanie wszystkich lewej rekursji
Poprzez utworzenie topologii zamawianie na nieterminali, powyższy proces może być rozszerzony również wyeliminować pośrednie lewej rekursji:
- Wejścia gramatyki: zestaw nieterminali i ich produkcjach
-
Wyjście Zmodyfikowany gramatyka generując tym samym językiem, ale bez lewej rekursji
-
Dla każdego nieterminalowi :
-
Powtarzać aż iteracji gramatyka pozostawia bez zmian:
-
Dla każdej reguły , jest sekwencją terminali i nieterminali:
-
Jeśli zaczyna się od nieterminalowi i :
- Pozwolić być bez swoich czołowych .
- Usuń regułę .
-
Dla każdej reguły :
- Dodaj regułę .
-
Jeśli zaczyna się od nieterminalowi i :
-
Dla każdej reguły , jest sekwencją terminali i nieterminali:
- Usuń lewy bezpośredniej rekursji dla jak opisano powyżej.
-
Powtarzać aż iteracji gramatyka pozostawia bez zmian:
-
Dla każdego nieterminalowi :
Należy zauważyć, że algorytm ten jest bardzo wrażliwy na nieterminalowi zamawiającego; optymalizacje często koncentrują się na wyborze tego zamawianie dobrze.
pułapki
Chociaż powyższe przekształcenia zachowania języka generowanego przez gramatykę, mogą zmienić drzew analizowania że świadek uznania strun. Dzięki odpowiedniej księgowości, drzewo przepisywanie można odzyskać oryginały, ale jeśli ten krok zostanie pominięty, różnice mogą zmienić semantykę do przetworzenia.
Łączność jest szczególnie podatny; lewy-asocjacyjne operatorzy zazwyczaj pojawiają się w prawym asocjacyjne podobny ustaleń wynikających z nowej gramatyki. Na przykład, wychodząc z tym gramatyki:
standardowe przekształcenia usunąć lewy rekursji otrzymując następujące:
Parsowania ciąg „1 - 2 - 3” z pierwszej gramatyki w parsera LALR (który może obsługiwać lewej rekurencyjnych gramatyk) skutkowałoby drzewie parsowania:
Tego parsowania grupy drzew warunki, na lewo, podając poprawne semantykę (1 - 2) - 3 .
Parsowania z drugiej daje gramatyka
które są odpowiednio interpretowane oznacza 1 + (-2 + (-3)) , a także prawidłowe, ale mniej wierny wejściu i znacznie trudniejsze do realizacji kilku operatorów. Wskazówki, jak warunki na prawo pojawić się głębiej w drzewie, podobnie jak gramatyka prawym rekurencyjne by ułożyć je na 1 - (2 - 3) .
Uwzględnienie lewej rekursji w Analiza zstępująca
Formalnej gramatyki , który zawiera lewy rekurencji nie może być analizowany przez LL (k) -parser lub innego naiwnego rekurencyjnego zejścia parsera chyba że jest konwertowany na słabo równoważnej formie prawym rekurencyjne. W przeciwieństwie do lewej rekursji jest korzystna dla parserami LALR ponieważ powoduje użycie stosu niższej niż prawe rekursji . Jednak bardziej wyrafinowane top-down parser może realizować ogólne gramatyk bezkontekstowych autorem stosowania ograniczenia. W 2006 roku Frost i Hafiz opisany algorytm, który może pomieścić niejednoznaczne gramatyk z bezpośrednich lewych-rekurencyjne zasad produkcji . Że algorytm został rozszerzony do kompletnej analizy składniowej algorytmu, aby pomieścić pośrednie jak i lewej bezpośredni rekurencji w wielomianowym czasie, a do generowania kompaktowych reprezentacje wielomian-size dotyczące liczby potencjalnie wykładniczej o drzewo wyprowadzenia dla wysoce niejednoznaczne gramatyk przez mróz, Hafiza i Callaghan w 2007 roku . autorzy następnie wdrożony algorytm jako zestaw kombinatorów parsera napisane w Haskell języku programowania.
Zobacz też
Bibliografia
- ^ Uwagi o teorii języka formalnego i parsowania , James Power, Wydział Informatyki National University of Ireland, Maynooth Maynooth, Co Kildare, Irlandia. JPR02
- ^ Moore, Robert C. (maj 2000). „Usuwanie Lewa rekursji z gramatyk bezkontekstowych” (PDF) . 6-ty Applied przetwarzanie języka naturalnego Konferencja : 249-255.
- ^ Frost, R .; Hafiz R. (2006). „A New Top-Down analizowaniem Algorytm pomieścić dwuznaczność i lewej rekursji w czasie wielomianowym” . ACM SIGPLAN Uwagi . 41 (5): 46-54. doi : 10.1145 / 1149982.1149988 .Dostępny od autora w http://hafiz.myweb.cs.uwindsor.ca/pub/p46-frost.pdf zarchiwizowanych 8.01.2015 w Wayback Maszynie
- ^ Frost, R .; R. Hafiz; P. Callaghan (czerwiec 2007). „Modułowa i wydajniejszy Top-Down analizowaniem za niejednoznaczne lewej rekurencyjnych gramatyk” (PDF) . 10. Międzynarodowe Warsztaty parsowania Technologies (IWPT), ACL-SIGPARSE : 109-120. Zarchiwizowane z oryginałem (PDF) na 2011-05-27.
- ^ Frost, R .; R. Hafiz; P. Callaghan (styczeń 2008). Parser kombinatorów dla niejednoznacznych zostawienie rekurencyjnych gramatyk (PDF) . 10. Międzynarodowe Sympozjum na temat praktycznych aspektów deklaratywnej języki (PADL), ACM-SIGPLAN . Lecture Notes in Computer Science. 4902 . ss. 167-181. doi : 10.1007 / 978-3-540-77442-6_12 . ISBN 978-3-540-77441-9,

