Specyfikacja podjęzyka WCCL L1
Podjęzyk L1 rozszerza L0 o:- zmienne typu TSET, STRSET, BOOL
- predykaty sprawdzające anotacje
- wyrażenia ustawiające wartość zmiennej na obrzeżu anotacji
Typy danych, składnia zapisu stałych i mechanizm zmiennych¶
Zmienne, ich składnia i zasięg¶
Mamy teraz zmienne czterech typów: pozycja, zbiór symboli z tagsetu, zbiór stringów, wartość logiczna.
Wskazanie zmiennej:$VAR
(pozycja)$s:VAR
(zbiór stringów)$t:VAR
(zbiór symboli z tagsetu)$b:VAR
(wartość logiczna)
Wskazanie zmiennej używane jest w kontekstach, gdzie wartość zmiennej będzie zmieniana (np. pierwszy argument operatora setvar
).
Odwołanie do zmiennej ma składnię identyczną ze wskazaniem zmiennej. Używane jest w pozostałych kontekstach, tj. wszędzie tam, gdzie interesuje nas pobranie wartości zmiennej, a nie jej zmiana.
Kontekst wystąpienia zmiennej określa jej rolę, np. w przypadku operatora setvar
pierwszy argument musi być wskazaniem zmiennej, a drugi — dowolnym wyrażeniem zwracającym wartość zmiennej, w szczególności może to być odwołanie do zmiennej.
Składnia i semantyka¶
Wyrażenie WCCL L1 to wyrażenie funkcyjne WCCL L1 (w L1 nie mamy jeszcze reguł, składni dla całych plików).
Wyrażenie funkcyjne WCCL L1 to- stała określonego typu lub
- odwołanie do zmiennej określonego typu lub
- operator zwracający wartość, czyli funkcja zwracająca wartość jednego ze zdefiniowanych wcześniej typów.
Ta definicja jest identyczna z definicją dla L0, z tym że dopuszczamy zmienne różnych typów oraz rozszerzamy zbiór operatorów.
Wyrażenie funkcyjne nie musi być czysto funkcyjne, tu chodzi o typ zwracanej wartości.
Odwołanie do zmiennej może być zaimplementowane jako operator. Ważne jest to, że wszystkie powyższe przypadki są dla nas wyrażeniami funkcyjnymi, które po aplikacji na kontekście zwracają wartość.
Wszystkie operatory z L0 są częścią L1.
Wyrażenia czysto funkcyjne¶
Predykaty sprawdzające anotacje¶
Operatory sprawdzające anotacje (na poziomie tokenów, nie dopasowań). Odtąd phrase_name
to nazwa frazy (typu pojedynczy string).
phrase(pos, phrase_name)
wtt. gdy przez podaną pozycję przechodzi anotacja o podanej nazwie (anotacja może się zamykać w podanej pozycji, może być większa)phrase_beg(pos, phrase_name)
wtt. gdy przez podaną pozycję przechodzi anotacja o podanej nazwie i jest to jej pierwszy tokenphrase_end(pos, phrase_name)
wtt. gdy przez podaną pozycję przechodzi anotacja o podanej nazwie i jest to jej ostatni tokenphrase_whole(pos1, pos2, phrase_name)
wtt. gdy ciągła anotacja zaczyna się na pos1
i kończy się na pos2
(ciągła anotacja może być fragmentem większej, nieciągłej; my sprawdzamy tylko ciągły kawałek)phrase_pp(pos1, pos2, phrase_name)
wtt. gdy obie pozycje należą do tej frazy tego samego typu i jest to albo ta sama ciągła fraza, albo dwa kawałki większej nieciągłej frazy (tj. należą do ciągłych anotacji o tych samych indeksach)
Wyrażenia zmieniające wartości zmiennych¶
Wyrażenia te zachowują się jak wyrażenia funkcyjne, lecz ich skutkiem ubocznym może być zmiana wartości zmiennych.
Iteracja za pomocą zmiennej¶
lphrase(pos1, posvar, phrase_name)
wtt. gdy phrase(pos1, phrase_name)
Skutki uboczne:
- w razie sukcesu,
posvar
jest ustawiana na pierwszy token frazy przechodzącej przezpos1
- w razie porażki (tj. gdy przez
pos1
nie przechodzi fraza o podanej nazwie),posvar
ustawiana jest nanowhere
- iterujemy tylko w ramach ciągłego kawałka frazy
Disaster: ops.p_phraseleft
rphrase(pos1, posvar, phrase_name)
wtt. gdy phrase(pos1, phrase_name)
Skutki uboczne:
- w razie sukcesu,
posvar
jest ustawiana na ostatni token frazy przechodzącej przezpos1
- w razie porażki,
posvar
ustawiana jest nanowhere
- iterujemy tylko w ramach ciągłego kawałka frazy
Disaster: ops.p_phraseright
lphrasewhole
, rphrasewhole
-- j.w., lecz frazy nieciągłe są obsługiowane, tj. ustawiamy się na skrajnym tokenie biorąc pod uwagę wszystkie kawałki frazy
phrasehead(pos1, posvar, phrase_name)
wtt. gdy phrase(pos1, phrase_name)
Skutki uboczne:
- w razie sukcesu,
posvar
jest ustawiana na pozycję będącą nadrzędnikiem frazy - w razie porażki,
posvar
ustawiana jest nanowhere
- nadrzędnik może znajdować się w innym kawałku niż ten, na którym stoi
pos1
, i tak go znajdziemy
TODO operatory sprawdzające relacje