diff --git a/src/main/scala/lisa/kernel/Printer.scala b/src/main/scala/lisa/kernel/Printer.scala index c5d2967ded8c571b051e165f166bf87c27d894cc..f367a551bade5d3d7904cf35eb1a3e63c5e35d34 100644 --- a/src/main/scala/lisa/kernel/Printer.scala +++ b/src/main/scala/lisa/kernel/Printer.scala @@ -258,6 +258,8 @@ object Printer { case RightSubstEq(_, t1, _, _, _, _) => pretty("R. SubstEq", t1) case LeftSubstIff(_, t1, _, _, _, _) => pretty("L. SubstIff", t1) case RightSubstIff(_, t1, _, _, _, _) => pretty("R. SubstIff", t1) + case InstantiateSchematicFunction(_, t1, _, _, _) => pretty("?Fun Instantiation", t1) + case InstantiateSchematicPredicate(_, t1, _, _, _) => pretty("?Pred Instantiation", t1) case SCSubproof(_, _, false) => pretty("SCSubproof (hidden)") case other => throw new Exception(s"No available method to print this proof step, consider updating Printer.scala\n$other") } diff --git a/src/main/scala/lisa/kernel/fol/FormulaDefinitions.scala b/src/main/scala/lisa/kernel/fol/FormulaDefinitions.scala index 8e1e772bde023e8c6bb5f7494a29e34e43620ce8..da0ab913031b47a7465a2d510c4568b47676060f 100644 --- a/src/main/scala/lisa/kernel/fol/FormulaDefinitions.scala +++ b/src/main/scala/lisa/kernel/fol/FormulaDefinitions.scala @@ -112,7 +112,7 @@ private[fol] trait FormulaDefinitions extends FormulaLabelDefinitions with TermD * Those variables are replaced by the actual arguments of p. * @return phi[psi(a1,..., an)/p] */ - def instantiatePredicateSchema(phi: Formula, p: SchematicPredicateLabel, psi: Formula, a: List[VariableLabel]): Formula = { + def instantiatePredicateSchema(phi: Formula, p: SchematicPredicateLabel, psi: Formula, a: Seq[VariableLabel]): Formula = { require(a.length == p.arity) phi match { case PredicateFormula(label, args) => @@ -139,7 +139,7 @@ private[fol] trait FormulaDefinitions extends FormulaLabelDefinitions with TermD * Those variables are replaced by the actual arguments of f. * @return phi[r(a1,..., an)/f] */ - def instantiateFunctionSchema(phi: Formula, f: SchematicFunctionLabel, r: Term, a: List[VariableLabel]): Formula = { + def instantiateFunctionSchema(phi: Formula, f: SchematicFunctionLabel, r: Term, a: Seq[VariableLabel]): Formula = { require(a.length == f.arity) phi match { case PredicateFormula(label, args) => PredicateFormula(label, args.map(instantiateFunctionSchema(_, f, r, a))) diff --git a/src/main/scala/lisa/kernel/fol/TermDefinitions.scala b/src/main/scala/lisa/kernel/fol/TermDefinitions.scala index 03411af89036811ad6b942419ba3f739c7daccfc..25c23e0e72aab95c21e93f1c7d0f1121d958388b 100644 --- a/src/main/scala/lisa/kernel/fol/TermDefinitions.scala +++ b/src/main/scala/lisa/kernel/fol/TermDefinitions.scala @@ -87,7 +87,7 @@ private[fol] trait TermDefinitions extends TermLabelDefinitions { * Those variables are replaced by the actual arguments of f. * @return t[r(a1,..., an)/f] */ - def instantiateFunctionSchema(t: Term, f: SchematicFunctionLabel, r: Term, a: List[VariableLabel]): Term = { + def instantiateFunctionSchema(t: Term, f: SchematicFunctionLabel, r: Term, a: Seq[VariableLabel]): Term = { require(a.length == f.arity) t match { case VariableTerm(label) => t diff --git a/src/main/scala/lisa/kernel/proof/SCProofChecker.scala b/src/main/scala/lisa/kernel/proof/SCProofChecker.scala index 372699abbe43d3a6f84c9d4e505cfc843ca599d2..f2e55a7ed4e5729b1fa0be48696bad0a10d56aab 100644 --- a/src/main/scala/lisa/kernel/proof/SCProofChecker.scala +++ b/src/main/scala/lisa/kernel/proof/SCProofChecker.scala @@ -401,6 +401,35 @@ object SCProofChecker { else (false, Nil, s"Right-hand side of the premise and the conclusion should be the same with each containing one of φ[τ/?q] and φ[ψ/?q], but it isn't the case." ) else (false, Nil, "Left-hand sides of the premise + ψ↔τ must be the same as left-hand side of the premise.") else (false, Nil, "Predicate schema ?q must have arity 0.") + /** + * <pre> + * Γ |- Δ + * --------------------- + * Γ[?f/r(a)] |- Δ[?f/r(a)] + * </pre> + */ + case InstantiateSchematicFunction(bot, t1, f, r, a) => + val expected = (ref(t1).left.map(phi => instantiateFunctionSchema(phi, f, r, a)), ref(t1).right.map(phi => instantiateFunctionSchema(phi, f, r, a))) + if (isSameSet(bot.left, expected._1)) + if (isSameSet(bot.right, expected._2)) + (true, Nil, "") + else (false, Nil, "Right-hand side of premise instantiated with [?f/r(a)] must be the same as right-hand side of conclusion.") + else (false, Nil, "Left-hand side of premise instantiated with [?f/r(a)] must be the same as left-hand side of conclusion.") + + /** + * <pre> + * Γ |- Δ + * --------------------- + * Γ[?p/ψ(a)] |- Δ[?p/ψ(a)] + * </pre> + */ + case InstantiateSchematicPredicate(bot, t1, p, psi, a) => + val expected = (ref(t1).left.map(phi => instantiatePredicateSchema(phi, p, psi, a)), ref(t1).right.map(phi => instantiatePredicateSchema(phi, p, psi, a))) + if (isSameSet(bot.left, expected._1)) + if (isSameSet(bot.right, expected._2)) + (true, Nil, "") + else (false, Nil, "Right-hand side of premise instantiated with [?p/ψ(a)] must be the same as right-hand side of conclusion.") + else (false, Nil, "Left-hand side of premise instantiated with [?p/ψ(a)] must be the same as left-hand side of conclusion.") case SCSubproof(sp, premises, _) => if (premises.size == sp.imports.size){ @@ -409,7 +438,7 @@ object SCProofChecker { val r_subproof = checkSCProof(sp) if (r_subproof._1) (true, Nil, "") - else (false, r_subproof._2, "Subproof reports an error:\n"+r_subproof._3) + else (false, r_subproof._2, r_subproof._3) } else (false, Nil, s"Premise number ${invalid.get._1} (refering to step ${invalid.get}) is not the same as import number ${invalid.get._1} of the subproof.") } else (false, Nil, "Number of premises and imports don't match: "+premises.size+" "+sp.imports.size) diff --git a/src/main/scala/lisa/kernel/proof/SequentCalculus.scala b/src/main/scala/lisa/kernel/proof/SequentCalculus.scala index cf79543367bde60c6c3ce6827dff22f56f695eaf..7dce18204a55474b2a23154f09d012b0d2a85b51 100644 --- a/src/main/scala/lisa/kernel/proof/SequentCalculus.scala +++ b/src/main/scala/lisa/kernel/proof/SequentCalculus.scala @@ -1,6 +1,7 @@ package lisa.kernel.proof -import lisa.kernel.fol.FOL._ +import lisa.kernel.fol.FOL.* + import scala.collection.immutable.Set @@ -276,6 +277,22 @@ object SequentCalculus { * </pre> */ case class RightSubstIff(bot: Sequent, t1: Int, fa: Formula, fb: Formula, phi: Formula, h: SchematicPredicateLabel) extends SCProofStep{val premises = Seq(t1)} + /** + * <pre> + * Γ |- Δ + * --------------------- + * Γ[?f/r(a)] |- Δ[?f/r(a)] + * </pre> + */ + case class InstantiateSchematicFunction(bot:Sequent, t1:Int, f:SchematicFunctionLabel, r:Term, a: Seq[VariableLabel] ) + /** + * <pre> + * Γ |- Δ + * --------------------- + * Γ[?p/ψ(a)] |- Δ[?p/ψ(a)] + * </pre> + */ + case class InstantiateSchematicPredicate(bot:Sequent, t1:Int, p:SchematicPredicateLabel, psi:Formula, a: Seq[VariableLabel] ) // Proof Organisation rules case class SCSubproof(sp: SCProof, premises: Seq[Int] = Seq.empty, display:Boolean = true) extends SCProofStep {