--- 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'))