""" Library containing all the basic functions """ # from ..proof import Context, Proof from ..props import Eq, Exists, Or, Prop from ..terms import ( App, Const, A1, A2, L1, L2, L3, Lambda, Term, register_known_const, register_known_norm ) # ----------------------------------------------------------------------------- # Identity function # ----------------------------------------------------------------------------- # Always returns its input. id_func = Lambda(lambda x : x) register_known_const("id", id_func) register_known_const("identity", id_func) # # ----------------------------------------------------------------------------- # # Equality # # ----------------------------------------------------------------------------- # equality = Lambda(Lambda(EqT(lhs=Var(1), rhs=Var(0)))) # register_known_const("eq", equality) # register_known_const("==", equality) # ----------------------------------------------------------------------------- # Bool # ----------------------------------------------------------------------------- bool_t = L2(lambda x, y : x).normalize() bool_f = L2(lambda x, y : y).normalize() if_statement = L3(lambda x, y, z : A2(x, y, z)).normalize() not_statement = L1(lambda b : A2(b, bool_f, bool_t)).normalize() register_known_const("Bool.False", bool_f) register_known_const("Bool.True", bool_t) register_known_const("Bool.elim", if_statement) register_known_const("Bool.if", if_statement) register_known_const("Bool.not", not_statement) def is_bool(x : Term) -> Prop: return Or(Eq(x=x, y=bool_f), Eq(x=x, y=bool_t)) # ----------------------------------------------------------------------------- # Nat # ----------------------------------------------------------------------------- zero = Const("Nat.Zero") succ = Const("Nat.Succ") def kernel_from_int(n : int) -> Term: if n < 0: raise ValueError( "Int is not Nat" ) t = zero for _ in range(n): t = A1(succ, t) return t def is_nat(x : Term) -> Prop: return Or( Eq(x=x, y=zero), Exists(lambda n : Eq(x=x, y=A1(Const("Nat.Succ"), n))), ) def __nat_add(t : Term) -> Term: match t: case App(f=Const("Nat.add"), x=Const("Nat.Zero")): return id_func case App(f=Const("Nat.add"), x=App(f=Const("Nat.Succ"), x=a)): return L1(lambda b : A1(succ, A2(Const("Nat.add"), a, b))) case _: return t register_known_norm(__nat_add) def __nat_leq(t : Term) -> Term: match t: case App(f=Const("Nat.leq"), x=Const("Nat.Zero")): return bool_t case App(App(f=Const("Nat.leq"), x=_), x=Const("Nat.Zero")): return bool_f case App(f=App(f=Const("Nat.leq"), x=App(f=Const("Nat.Succ"), x=a)), x=App(f=Const("Nat.Succ"), x=b)): return A2(Const("Nat.leq"), a, b) case _: return t register_known_norm(__nat_leq)