Skip to content
Snippets Groups Projects
Commit 1a6a2be3 authored by Etienne Kneuss's avatar Etienne Kneuss
Browse files

ADTDual

parent 0e8b6e66
No related branches found
No related tags found
No related merge requests found
...@@ -246,6 +246,8 @@ object Definitions { ...@@ -246,6 +246,8 @@ object Definitions {
fields.map(f => f.id).toSet fields.map(f => f.id).toSet
} }
def fieldsIds = fields.map(_.id)
def selectorID2Index(id: Identifier) : Int = { def selectorID2Index(id: Identifier) : Int = {
var i : Int = 0 var i : Int = 0
var found = false var found = false
......
...@@ -9,6 +9,7 @@ object Rules { ...@@ -9,6 +9,7 @@ object Rules {
def all(synth: Synthesizer) = List( def all(synth: Synthesizer) = List(
new Unification.DecompTrivialClash(synth), new Unification.DecompTrivialClash(synth),
new Unification.OccursCheck(synth), new Unification.OccursCheck(synth),
new ADTDual(synth),
new OnePoint(synth), new OnePoint(synth),
new Ground(synth), new Ground(synth),
new CaseSplit(synth), new CaseSplit(synth),
...@@ -243,3 +244,38 @@ object Unification { ...@@ -243,3 +244,38 @@ object Unification {
} }
} }
} }
class ADTDual(synth: Synthesizer) extends Rule("ADTDual", synth) {
def isApplicable(task: Task): List[DecomposedTask] = {
val p = task.problem
val xs = p.xs.toSet
val as = p.as.toSet
val TopLevelAnds(exprs) = p.phi
val (toRemove, toAdd, toPre) = exprs.collect {
case eq @ Equals(cc @ CaseClass(cd, args), e) if (variablesOf(e) -- as).isEmpty && (variablesOf(cc) -- xs).isEmpty =>
(eq, (cd.fieldsIds zip args).map{ case (id, ex) => Equals(ex, CaseClassSelector(cd, e, id)) }, CaseClassInstanceOf(cd, e) )
case eq @ Equals(e, cc @ CaseClass(cd, args)) if (variablesOf(e) -- as).isEmpty && (variablesOf(cc) -- xs).isEmpty =>
(eq, (cd.fieldsIds zip args).map{ case (id, ex) => Equals(ex, CaseClassSelector(cd, e, id)) }, CaseClassInstanceOf(cd, e) )
}.unzip3
if (!toRemove.isEmpty) {
val sub = p.copy(phi = And((exprs.toSet -- toRemove ++ toAdd.flatten).toSeq))
val onSuccess: List[Solution] => Solution = {
case List(s) =>
Solution(And(s.pre +: toPre), s.term)
case _ =>
Solution.none
}
List(task.decompose(this, List(sub), onSuccess, 80))
} else {
Nil
}
}
}
...@@ -64,11 +64,11 @@ class Synthesizer(val r: Reporter, val solvers: List[Solver]) { ...@@ -64,11 +64,11 @@ class Synthesizer(val r: Reporter, val solvers: List[Solver]) {
} }
def onTaskSucceeded(task: Task, solution: Solution) { def onTaskSucceeded(task: Task, solution: Solution) {
info(" => Solved "+task.problem+" ⊢ "+solution)
if (task.parent eq null) { if (task.parent eq null) {
info(" SUCCESS!") info(" SUCCESS!")
this.solution = Some(solution) this.solution = Some(solution)
} else { } else {
info(" => Solved "+task.problem+" ⊢ "+solution)
task.parent.subSucceeded(task.problem, solution) task.parent.subSucceeded(task.problem, solution)
} }
} }
......
...@@ -12,6 +12,8 @@ object UnificationSynthesis { ...@@ -12,6 +12,8 @@ object UnificationSynthesis {
def u5(a1: Int): List = choose { (xs: List) => Cons(a1, Nil()) == xs } def u5(a1: Int): List = choose { (xs: List) => Cons(a1, Nil()) == xs }
def u6(a1: List): Int = choose { (xs: Int) => Cons(xs, Nil()) == a1 }
sealed abstract class List sealed abstract class List
case class Nil() extends List case class Nil() extends List
case class Cons(head : Int, tail : List) extends List case class Cons(head : Int, tail : List) extends List
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment