From 2514260b5ff7c1ac3c845f75c9e5fd82915df366 Mon Sep 17 00:00:00 2001 From: breandan Date: Tue, 8 Oct 2024 00:33:50 -0400 Subject: [PATCH] test non-emptiness latency for nontrivial intersection --- .../kaliningraph/parsing/Grammars.kt | 1 + .../hypergraph/kaliningraph/automata/JFSA.kt | 12 ++++++---- .../kaliningraph/automata/WFSATest.kt | 24 +++++++++++++++++++ 3 files changed, 32 insertions(+), 5 deletions(-) diff --git a/src/commonTest/kotlin/ai/hypergraph/kaliningraph/parsing/Grammars.kt b/src/commonTest/kotlin/ai/hypergraph/kaliningraph/parsing/Grammars.kt index 18deb9ec..8e3cc819 100644 --- a/src/commonTest/kotlin/ai/hypergraph/kaliningraph/parsing/Grammars.kt +++ b/src/commonTest/kotlin/ai/hypergraph/kaliningraph/parsing/Grammars.kt @@ -25,6 +25,7 @@ object Grammars { S -> X | Y | Z """.parseCFG().noNonterminalStubs + val dyck = """S -> ( ) | ( S ) | S S""".parseCFG().noEpsilonOrNonterminalStubs val deadSimple = """S -> ( ) | ( S )""".parseCFG().noEpsilonOrNonterminalStubs val dsNorm = """ START -> START START diff --git a/src/jvmMain/kotlin/ai/hypergraph/kaliningraph/automata/JFSA.kt b/src/jvmMain/kotlin/ai/hypergraph/kaliningraph/automata/JFSA.kt index d2584e49..8aaacf99 100644 --- a/src/jvmMain/kotlin/ai/hypergraph/kaliningraph/automata/JFSA.kt +++ b/src/jvmMain/kotlin/ai/hypergraph/kaliningraph/automata/JFSA.kt @@ -57,7 +57,12 @@ data class FSATrajectory(val traj: List<Σᐩ?>, val lastState: BState, val scor fun BAutomaton.min(): BAutomaton = minimize(this) -fun PTree.toDFA(minimize: Boolean = false) = +fun PTree.toDFA( + minimize: Boolean = false, + unitRule: (String) -> dk.brics.automaton.Automaton = { + BAutomaton.makeChar(Random(it.hashCode()).nextInt().toChar()) + } +) = measureTimedValue { BAutomaton.setMinimization(MINIMIZE_BRZOZOWSKI) var i = 0 @@ -68,10 +73,7 @@ fun PTree.toDFA(minimize: Boolean = false) = else if (i++ % 13 == 0) a.concatenate(b).min() else a.concatenate(b) }, either = { a, b -> if (a == null) b else if (b == null) a else if (j++ % 13 == 0) a.union(b).min() else a.union(b) }, - unit = { a -> - if ("ε" in a.root) null - else BAutomaton.makeChar(Random(a.root.hashCode()).nextInt().toChar()) - } + unit = { a -> if ("ε" in a.root) null else unitRule(a.root) } ) }.also { println("Took ${it.duration} to build FSA") }.value ?.also { println("Original automata had ${it diff --git a/src/jvmTest/kotlin/ai/hypergraph/kaliningraph/automata/WFSATest.kt b/src/jvmTest/kotlin/ai/hypergraph/kaliningraph/automata/WFSATest.kt index ba227d9c..5f243e2a 100644 --- a/src/jvmTest/kotlin/ai/hypergraph/kaliningraph/automata/WFSATest.kt +++ b/src/jvmTest/kotlin/ai/hypergraph/kaliningraph/automata/WFSATest.kt @@ -10,6 +10,7 @@ import net.jhoogland.jautomata.* import net.jhoogland.jautomata.operations.Concatenation import net.jhoogland.jautomata.semirings.RealSemiring import java.io.File +import kotlin.system.measureTimeMillis import kotlin.test.* import kotlin.time.measureTimedValue @@ -72,6 +73,29 @@ class WFSATest { println(BAutomaton.minimize(ag.also { it.determinize() }).toDot()) } +/* +./gradlew jvmTest --tests "ai.hypergraph.kaliningraph.automata.WFSATest.testIntersectionNonemptiness" +*/ + @Test + fun testIntersectionNonemptiness() { + val ab = BAutomaton.makeString("(").concatenate(BAutomaton.makeString(")")) + val aa = BAutomaton.makeString("(").concatenate(BAutomaton.makeString("(")) + val ac = BAutomaton.makeString("(") + val az = RegExp("(\\(+(\\(+\\)+){3,15}\\)+)+").toAutomaton() + + val ds = Grammars.dyck.startPTree(List(20) { "_" })!! + .toDFA(false) { BAutomaton.makeString(it) }!! + + val a = ab.union(aa).union(ac) + val ag = a.repeat(19, 25).union(az) + println("SA:" + ag.getShortestExample(true)) + println("SD:" + ds.getShortestExample(true)) + println("SS:" + ds.intersection(ag).getShortestExample(true)) + + measureTimeMillis { println(!ds.intersection(ag).isEmpty) } + .also { println("Time: $it ms") } + } + /* ./gradlew jvmTest --tests "ai.hypergraph.kaliningraph.automata.WFSATest.testPTreeVsWFSA" */