summaryrefslogtreecommitdiff
path: root/edit-lens/src/Control/FST.lhs
diff options
context:
space:
mode:
authorGregor Kleen <gkleen@yggdrasil.li>2019-06-07 09:08:42 +0200
committerGregor Kleen <gkleen@yggdrasil.li>2019-06-07 09:08:42 +0200
commita29cce747f3717e32231c9a92b40be12832037b6 (patch)
tree70f399682dec8657719eae4358e87cdc24bbf42f /edit-lens/src/Control/FST.lhs
parent9a02751c1e588a5bbb83bb7e543c26486d3079d5 (diff)
downloadincremental-dfsts-a29cce747f3717e32231c9a92b40be12832037b6.tar
incremental-dfsts-a29cce747f3717e32231c9a92b40be12832037b6.tar.gz
incremental-dfsts-a29cce747f3717e32231c9a92b40be12832037b6.tar.bz2
incremental-dfsts-a29cce747f3717e32231c9a92b40be12832037b6.tar.xz
incremental-dfsts-a29cce747f3717e32231c9a92b40be12832037b6.zip
Finish for submission
Diffstat (limited to 'edit-lens/src/Control/FST.lhs')
-rw-r--r--edit-lens/src/Control/FST.lhs33
1 files changed, 16 insertions, 17 deletions
diff --git a/edit-lens/src/Control/FST.lhs b/edit-lens/src/Control/FST.lhs
index 9cc7524..165f247 100644
--- a/edit-lens/src/Control/FST.lhs
+++ b/edit-lens/src/Control/FST.lhs
@@ -47,12 +47,12 @@ import Text.Dot
47\end{comment} 47\end{comment}
48 48
49\begin{defn}[Finite State Transducers] 49\begin{defn}[Finite State Transducers]
50Unter einem \emph{finite state transducer} verstehen wir ein 6-Tupel $(\Sigma, \Delta, Q, I, F, E)$ mit $\Sigma$ dem endlichen Eingabe-Alphabet, $\Delta$ dem endlichen Ausgabe-Alphabet, $Q$ einer endlichen Menge an Zuständen, $I \subset Q$ der Menge von initialen Zuständen, $F \subset Q$ der Menge von akzeptierenden Endzuständen, und $E \subset Q \times (\Sigma \cup \{ \epsilon \}) \times (\Delta \cup \{ \epsilon \}) \times Q$ der Transitionsrelation. 50Unter einem \emph{finite state transducer} verstehen wir ein 6-Tupel $(\Sigma, \Delta, Q, I, F, E)$ mit $\Sigma$ dem endlichen Eingabe-Alphabet, $\Delta$ dem endlichen Ausgabe-Alphabet, $Q$ einer endlichen Menge an Zuständen, $I \subset Q$ der Menge von initialen Zuständen, $F \subset Q$ der Menge von akzeptierenden Endzuständen und $E \subset Q \times (\Sigma \cup \{ \epsilon \}) \times (\Delta \cup \{ \epsilon \}) \times Q$ der Transitionsrelation.
51 51
52Semantisch ist ein finite state transducer ein endlicher Automat erweitert um die Fähigkeit bei Zustandsübergängen ein Symbol aus seinem Ausgabe-Alphabet an ein Ausgabe-Wort anzuhängen. 52Semantisch ist ein finite state transducer ein endlicher Automat, erweitert um die Fähigkeit bei Zustandsübergängen ein Symbol aus seinem Ausgabe-Alphabet an ein Ausgabe-Wort anzuhängen (Siehe Definition \ref{defn:fst-eval}).
53 53
54In Haskell lockern wir die Anforderung, dass die Ein- und Ausgabe-Alphabete endlich sein müssen und annotieren sie nur im Typsystem. 54In Haskell lockern wir die Anforderung, dass die Ein- und Ausgabe-Alphabete endlich sein müssen und annotieren sie nur im Typsystem.
55Zudem speichern wir die Transitionsrelation als multimap um effiziente lookups von Zustand-Eingabe-Paaren zu ermöglichen. 55Zudem speichern wir die Transitionsrelation als multimap, um effiziente lookups von Zustand-Eingabe-Paaren zu ermöglichen.
56 56
57\begin{code} 57\begin{code}
58data FST state input output = FST 58data FST state input output = FST
@@ -64,7 +64,7 @@ data FST state input output = FST
64\end{defn} 64\end{defn}
65 65
66\begin{eg} \label{eg:linebreak} 66\begin{eg} \label{eg:linebreak}
67 Als wiederkehrendes Beispiel betrachten wir einen Transducer $L_{80} = (\Sigma, \Delta, Q, I, F, E)$, der für ein beliebiges Alphabet $\Sigma \supseteq \{ \text{\tt ' '}, \text{\tt \textbackslash n} \}$ durch Umwandlung zwischen Leerzeichen und Zeilenumbrüchen sicherstellt, dass jede Zeile des Ausgabetextes möglichst wenige aber mindestens 80 Zeichen enthält, und nur an Wortgrenzen umbricht: 67 Als wiederkehrendes Beispiel betrachten wir einen Transducer $L_{80} = (\Sigma, \Delta, Q, I, F, E)$, der für ein beliebiges Alphabet $\Sigma \supseteq \{ \text{\tt ' '}, \text{\tt \textbackslash n} \}$ durch Umwandlung zwischen Leerzeichen und Zeilenumbrüchen sicherstellt, dass jede Zeile des Ausgabetextes möglichst wenige, aber mindestens 80 Zeichen enthält und nur an Wortgrenzen umbricht:
68 68
69 \begin{align*} 69 \begin{align*}
70 \Delta & = \Sigma \\ 70 \Delta & = \Sigma \\
@@ -103,7 +103,7 @@ data FST state input output = FST
103 \draw[-] (rest)--(i.north); 103 \draw[-] (rest)--(i.north);
104 \draw[-] (rest)--(si.west); 104 \draw[-] (rest)--(si.west);
105 \end{tikzpicture} 105 \end{tikzpicture}
106 \caption{\label{fig:linebreak} Ein Transducer der, durch Übersetzung zwischen Leerzeichen und Zeilenumbrüchen, sicher stellt, dass jede Zeile eines Texts mindestens 80 Zeichen hat} 106 \caption{\label{fig:linebreak} Ein Transducer der durch Übersetzung zwischen Leerzeichen und Zeilenumbrüchen sicher stellt, dass jede Zeile eines Texts mindestens 80 Zeichen hat}
107 \end{figure} 107 \end{figure}
108\end{eg} 108\end{eg}
109 109
@@ -131,8 +131,8 @@ instance (Show state, Show input, Show output, Ord state, Ord input, Ord output)
131\end{code} 131\end{code}
132\end{comment} 132\end{comment}
133 133
134\begin{defn}[Auswertung von FSTs] 134\begin{defn}[Auswertung von FSTs] \label{defn:fst-eval}
135Wir definieren die \emph{Auswertung} von finite state transducers induktiv indem wir zunächst angeben wie ein einzelner Auswertungs-Schritt erfolgt. 135Wir definieren die \emph{Auswertung} von finite state transducers induktiv, indem wir zunächst angeben, wie ein einzelner Auswertungs-Schritt erfolgt.
136 136
137Hierzu kommentieren wir die Haskell-Implementierung eines Auswertungs-Schritts. 137Hierzu kommentieren wir die Haskell-Implementierung eines Auswertungs-Schritts.
138Notwendigerweise ist die Auswertung eines FSTs nicht deterministisch, wir produzieren daher eine Liste von möglichen Resultaten in keiner besonderen Reihenfolge. 138Notwendigerweise ist die Auswertung eines FSTs nicht deterministisch, wir produzieren daher eine Liste von möglichen Resultaten in keiner besonderen Reihenfolge.
@@ -145,7 +145,7 @@ step :: forall input output state. (Ord input, Ord output, Ord state)
145 -> [(Maybe input, state, Maybe output)] -- ^ Tuples of unconsumed input, next state, and produced output 145 -> [(Maybe input, state, Maybe output)] -- ^ Tuples of unconsumed input, next state, and produced output
146step FST{..} Nothing inS = (\s -> (inS, s, Nothing)) <$> Set.toList stInitial 146step FST{..} Nothing inS = (\s -> (inS, s, Nothing)) <$> Set.toList stInitial
147\end{code} 147\end{code}
148Ist kein vorheriger Schritt erfolgt so wählen wir einen initialen Zustand, konsumieren keine Eingabe, und produzieren keine Ausgabe. 148Ist kein vorheriger Schritt erfolgt, so wählen wir einen initialen Zustand, konsumieren keine Eingabe und produzieren keine Ausgabe.
149 149
150\begin{code} 150\begin{code}
151step FST{..} (Just c) inS = let 151step FST{..} (Just c) inS = let
@@ -154,7 +154,7 @@ step FST{..} (Just c) inS = let
154 in Set.toList $ Set.map (\(n, mOut) -> (Nothing, n, mOut)) consuming `Set.union` Set.map (\(n, mOut) -> (inS, n, mOut)) unconsuming 154 in Set.toList $ Set.map (\(n, mOut) -> (Nothing, n, mOut)) consuming `Set.union` Set.map (\(n, mOut) -> (inS, n, mOut)) unconsuming
155\end{code} 155\end{code}
156Ansonsten wählen wir einen Eintrag aus der Transitionstabelle für den aktuellen Zustand, der entweder keine oder die gegebene Eingabe konsumiert. 156Ansonsten wählen wir einen Eintrag aus der Transitionstabelle für den aktuellen Zustand, der entweder keine oder die gegebene Eingabe konsumiert.
157Im Ergebnis geben wir den nächsten Zustand, die Ausgabe aus der Transitionstabelle, und ob die Eingabe konsumiert wurde an. 157Im Ergebnis geben wir den nächsten Zustand, die Ausgabe aus der Transitionstabelle und ob die Eingabe konsumiert wurde, an.
158 158
159\begin{code} 159\begin{code}
160runFST' :: forall input output state. (Ord input, Ord output, Ord state) 160runFST' :: forall input output state. (Ord input, Ord output, Ord state)
@@ -199,9 +199,8 @@ akzeptierenden Endzustände liegt.
199\end{comment} 199\end{comment}
200\end{defn} 200\end{defn}
201 201
202Es ist gelegentlich nützlich nur die möglichen Ausgaben eines FST auf gegebener 202Es ist gelegentlich nützlich nur die möglichen Ausgaben eines FST auf gegebener Eingabe zu bestimmen.
203Eingabe zu bestimmen, wir führen eine Hilfsfunktion auf Basis von 203Wir führen eine Hilfsfunktion auf Basis von {\ttfamily runFST'} ein:
204{\ttfamily runFST'} ein:
205 204
206\begin{code} 205\begin{code}
207runFST :: forall input output state. (Ord input, Ord output, Ord state) => FST state input output -> Seq input -> [Seq output] 206runFST :: forall input output state. (Ord input, Ord output, Ord state) => FST state input output -> Seq input -> [Seq output]
@@ -216,14 +215,14 @@ runFST = fmap (map $ catMaybes . fmap (view _2) . view _2) . runFST'
216\end{comment} 215\end{comment}
217 216
218Wir können das Produkt zweier FSTs definieren. 217Wir können das Produkt zweier FSTs definieren.
219Intuitiv wollen wir beide FSTs gleichzeitig ausführen und dabei sicherstellen, dass Ein- und Ausgabe der FSTs übereinstimmen\footnote{Da wir $\epsilon$-Transitionen in FSTs erlauben müssen wir uns festlegen wann eine $\epsilon$-Transition übereinstimmt mit einer anderen Transition. Wir definieren, dass $\epsilon$ als Eingabe ausschließlich mit $\epsilon$ übereinstimmt.}. 218Intuitiv wollen wir beide FSTs gleichzeitig ausführen und dabei sicherstellen, dass Ein- und Ausgabe der FSTs übereinstimmen\footnote{Da wir $\epsilon$-Transitionen in FSTs erlauben, müssen wir uns festlegen, wann eine $\epsilon$-Transition übereinstimmt mit einer anderen Transition. Wir definieren, dass $\epsilon$ als Eingabe ausschließlich mit $\epsilon$ übereinstimmt.}.
220 219
221Hierfür berechnen wir das Graphen-Produkt der FSTs: 220Hierfür berechnen wir das Graphen-Produkt der FSTs:
222 221
223\begin{defn}[FST-Produkt] 222\begin{defn}[FST-Produkt]
224 Gegeben zwei finite state transducer $T = (\Sigma, \Delta, Q, I, F, E)$ und $T^\prime = (\Sigma^\prime, \Delta^\prime, Q^\prime, I^\prime, F^\prime, E^\prime)$ nennen wir $T^\times = (\Sigma^\times, \Delta^\times, Q^\times, I^\times, F^\times, E^\times)$ das Produkt $T^\times = T \times T^\prime$ von $T$ und $T^\prime$. 223 Gegeben zwei finite state transducer $T = (\Sigma, \Delta, Q, I, F, E)$ und $T^\prime = (\Sigma^\prime, \Delta^\prime, Q^\prime, I^\prime, F^\prime, E^\prime)$ nennen wir $T^\times = (\Sigma^\times, \Delta^\times, Q^\times, I^\times, F^\times, E^\times)$ das Produkt $T^\times = T \times T^\prime$ von $T$ und $T^\prime$.
225 224
226 $T^\times$ bestimmt sich als das Graphenprodukt der beiden, die FSTs unterliegenden, Graphen wobei wir die Zustandsübergänge als Kanten mit Gewichten aus dem Boolschen Semiring auffassen: 225 $T^\times$ wird bestimmt als das Graphenprodukt der beiden die FSTs unterliegenden Graphen wobei wir die Zustandsübergänge als Kanten mit Gewichten aus dem Boolschen Semiring auffassen:
227 226
228 \begin{align*} 227 \begin{align*}
229 \Sigma^\times & = \Sigma \cap \Sigma^\prime \\ 228 \Sigma^\times & = \Sigma \cap \Sigma^\prime \\
@@ -271,7 +270,7 @@ productFST fst1 fst2 = FST
271Es ist später erforderlich einen FST derart einzuschränken, dass er eine gegebene Ausgabe produziert. 270Es ist später erforderlich einen FST derart einzuschränken, dass er eine gegebene Ausgabe produziert.
272 271
273Hierzu nehmen wir das FST-Produkt mit einem FST, der, ungeachtet der Eingabe, immer die gewünschte Ausgabe produziert. 272Hierzu nehmen wir das FST-Produkt mit einem FST, der, ungeachtet der Eingabe, immer die gewünschte Ausgabe produziert.
274Da die Ausgaben der beiden FSTs übereinstimmen müssen produziert das Produkt mit einem derartigen FST (solange dessen Ausgabe in keinem Sinne von der Eingabe abhängt) die gewünschte Ausgabe. 273Da die Ausgaben der beiden FSTs übereinstimmen müssen, produziert das Produkt mit einem derartigen FST (solange dessen Ausgabe in keinem Sinne von der Eingabe abhängt) die gewünschte Ausgabe.
275 274
276Zur Konstruktion eines derartigen \emph{Wort-FST}s nehmen wir Indizes im Ausgabe-Wort (natürliche Zahlen) als Zustände. 275Zur Konstruktion eines derartigen \emph{Wort-FST}s nehmen wir Indizes im Ausgabe-Wort (natürliche Zahlen) als Zustände.
277Übergänge sind immer entweder der Form $n \rightarrow \text{succ}(n)$, konsumieren keine Eingabe ($\epsilon$) und produzieren als Ausgabe das Zeichen am Index $n$ im Ausgabe-Wort, oder der Form $n \overset{(\sigma, \epsilon)}{\rightarrow} n$, für jedes Eingabesymbol $\sigma$ (um die Unabhängigkeit von der Eingabe sicherzustellen). 276Übergänge sind immer entweder der Form $n \rightarrow \text{succ}(n)$, konsumieren keine Eingabe ($\epsilon$) und produzieren als Ausgabe das Zeichen am Index $n$ im Ausgabe-Wort, oder der Form $n \overset{(\sigma, \epsilon)}{\rightarrow} n$, für jedes Eingabesymbol $\sigma$ (um die Unabhängigkeit von der Eingabe sicherzustellen).
@@ -335,7 +334,7 @@ wordFST inps outs = FST
335 \end{figure} 334 \end{figure}
336\end{eg} 335\end{eg}
337 336
338Da \texttt{wordFST} zur Konstruktion eine komprehensive Menge aller Eingabesymbole benötigt verwenden wir im folgenden eine optimierte Variante des Produkts mit einem Wort-FST. 337Da \texttt{wordFST} zur Konstruktion eine komprehensive Menge aller Eingabesymbole benötigt, verwenden wir im Folgenden eine optimierte Variante des Produkts mit einem Wort-FST.
339 338
340\begin{code} 339\begin{code}
341restrictOutput :: forall state input output. (Ord state, Ord input, Ord output) => Seq output -> FST state input output -> FST (Natural, state) input output 340restrictOutput :: forall state input output. (Ord state, Ord input, Ord output) => Seq output -> FST state input output -> FST (Natural, state) input output
@@ -381,7 +380,7 @@ restrictOutput :: forall state input output. (Ord state, Ord input, Ord output)
381\begin{rem} 380\begin{rem}
382 Es ist bemerkenswert, dass in Beispiel \ref{eg:l80timesw100} die zirkuläre Struktur von $L_{80}$ durch das Produkt mit einem Wort verloren geht. 381 Es ist bemerkenswert, dass in Beispiel \ref{eg:l80timesw100} die zirkuläre Struktur von $L_{80}$ durch das Produkt mit einem Wort verloren geht.
383 382
384 I.\@A.\@ ist das Produkt eines beliebigen FST mit einem Wort-FST zwar nicht azyklisch, erbt jedoch die lineare Struktur des Wort-FST in dem Sinne, dass Fortschritt in Richtung der akzeptierenden Zustände nur möglich ist indem der $(i, \sigma, w_i, i + 1)$-Klasse von Transitionen des Wort-FSTs gefolgt wird. 383 I.\@A.\@ ist das Produkt eines beliebigen FST mit einem Wort-FST zwar nicht azyklisch, erbt jedoch die lineare Struktur des Wort-FST in dem Sinne, dass Fortschritt in Richtung der akzeptierenden Zustände nur möglich ist, indem der $(i, \sigma, w_i, i + 1)$-Klasse von Transitionen des Wort-FSTs gefolgt wird.
385\end{rem} 384\end{rem}
386 385
387\begin{comment} 386\begin{comment}