diff -r 53e7da9f372a -r 53f08d873e09 progs/matcher/re3.sc --- a/progs/matcher/re3.sc Fri Sep 15 10:49:33 2023 +0100 +++ b/progs/matcher/re3.sc Sun Sep 17 19:12:57 2023 +0100 @@ -1,4 +1,6 @@ -// A version with simplification of derivatives; +// A version of the matcher with simplification +// of derivatives +// // this keeps the regular expressions small, which // is good for the run-time // @@ -48,6 +50,7 @@ if (i == 0) ZERO else SEQ(der(c, r), NTIMES(r, i - 1)) } +// simplification def simp(r: Rexp) : Rexp = r match { case ALT(r1, r2) => (simp(r1), simp(r2)) match { case (ZERO, r2s) => r2s @@ -64,26 +67,23 @@ case r => r } - - // the derivative w.r.t. a string (iterates der) def ders(s: List[Char], r: Rexp) : Rexp = s match { case Nil => r case c::s => ders(s, simp(der(c, r))) } - // the main matcher function def matcher(r: Rexp, s: String) : Boolean = nullable(ders(s.toList, r)) +// Test Cases +//============ + // one or zero def OPT(r: Rexp) = ALT(r, ONE) - -// Test Cases - // evil regular expressions: (a?){n} a{n} and (a*)* b def EVIL1(n: Int) = SEQ(NTIMES(OPT(CHAR('a')), n), NTIMES(CHAR('a'), n)) val EVIL2 = SEQ(STAR(STAR(CHAR('a'))), CHAR('b'))