diff -r 46eee459a999 -r 66adcae6c762 handouts/ho06.tex --- a/handouts/ho06.tex Thu Oct 05 14:36:54 2023 +0100 +++ b/handouts/ho06.tex Fri Oct 13 15:07:37 2023 +0100 @@ -107,16 +107,20 @@ class we specify that \texttt{I} is the \emph{input type} of the parser combinator and that \texttt{T} is the \emph{output type}. This implies that the function \texttt{parse} takes an argument of type -\texttt{I} and returns a set of type \mbox{\texttt{Set[(T, I)]}}. +\texttt{I} and returns a set of type \mbox{\texttt{Set[(T, + I)]}}.\footnote{In the actual code on KEATS there is some + kerfuffle about correct type-bounds and using clauses. Ignore this + part of the implementation for the moment---it is not needed for + understanding how the code works.} \begin{center} \begin{lstlisting}[language=Scala] -abstract class Parser[I, T](using is: I => Seq[_]) { +abstract class Parser[I, T] { def parse(in: I): Set[(T, I)] def parse_all(in: I) : Set[T] = for ((hd, tl) <- parse(in); - if is(tl).isEmpty) yield hd + if tl.isEmpty) yield hd } \end{lstlisting} \end{center} @@ -214,8 +218,7 @@ \begin{lstlisting}[language=Scala, numbers=none] class AltParser[I, T] (p: => Parser[I, T], - q: => Parser[I, T])(using I => Seq[_]) - extends Parser[I, T] { + q: => Parser[I, T]) extends Parser[I, T] { def parse(in: I) = p.parse(in) ++ q.parse(in) } \end{lstlisting} @@ -306,8 +309,7 @@ \begin{lstlisting}[language=Scala,numbers=none] class SeqParser[I, T, S] (p: => Parser[I, T], - q: => Parser[I, S])(using I => Seq[_]) - extends Parser[I, (T, S)] { + q: => Parser[I, S]) extends Parser[I, (T, S)] { def parse(in: I) = for ((output1, u1) <- p.parse(in); (output2, u2) <- q.parse(u1)) @@ -483,7 +485,7 @@ \begin{lstlisting}[language=Scala,basicstyle=\small\ttfamily, numbers=none] class MapParser[I, T, S] (p: => Parser[I, T], - f: T => S)(using I => Seq[_]) extends Parser[I, S] { + f: T => S) extends Parser[I, S] { def parse(in: I) = for ((hd, tl) <- p.parse(in)) yield (f(hd), tl) } @@ -593,7 +595,7 @@ \texttt{Int}. Now \texttt{parse} generates \texttt{Set((123,abc))}, but this time \texttt{123} is an \texttt{Int}. Think carefully what the input and output type of the parser is without the semantic action -adn what with the semantic action (the type of the function can +and what with the semantic action (the type of the function can already tell you). Let us come back to semantic actions when we are going to implement actual context-free grammars.