feat(frontends/lean/structure_cmd): add 'eta' theorem for structures
This commit is contained in:
parent
101e9966fd
commit
c306bfa83c
3 changed files with 53 additions and 1 deletions
|
@ -29,6 +29,7 @@ Author: Leonardo de Moura
|
||||||
#include "library/definitional/induction_on.h"
|
#include "library/definitional/induction_on.h"
|
||||||
#include "library/definitional/cases_on.h"
|
#include "library/definitional/cases_on.h"
|
||||||
#include "library/definitional/unit.h"
|
#include "library/definitional/unit.h"
|
||||||
|
#include "library/definitional/eq.h"
|
||||||
#include "library/definitional/projection.h"
|
#include "library/definitional/projection.h"
|
||||||
#include "frontends/lean/parser.h"
|
#include "frontends/lean/parser.h"
|
||||||
#include "frontends/lean/util.h"
|
#include "frontends/lean/util.h"
|
||||||
|
@ -572,6 +573,10 @@ struct structure_cmd_fn {
|
||||||
save_info(n, "projection", m_name_pos);
|
save_info(n, "projection", m_name_pos);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void save_thm_info(name const & n) {
|
||||||
|
save_info(n, "theorem", m_name_pos);
|
||||||
|
}
|
||||||
|
|
||||||
void declare_projections() {
|
void declare_projections() {
|
||||||
m_env = mk_projections(m_env, m_name, m_modifiers.is_class());
|
m_env = mk_projections(m_env, m_name, m_modifiers.is_class());
|
||||||
for (expr const & field : m_fields) {
|
for (expr const & field : m_fields) {
|
||||||
|
@ -650,6 +655,36 @@ struct structure_cmd_fn {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void declare_eta() {
|
||||||
|
if (!has_eq_decls(m_env))
|
||||||
|
return;
|
||||||
|
level_param_names lnames = to_list(m_level_names.begin(), m_level_names.end());
|
||||||
|
levels st_ls = param_names_to_levels(lnames);
|
||||||
|
expr st_type = mk_app(mk_constant(m_name, st_ls), m_params);
|
||||||
|
expr st = mk_local(m_ngen.next(), "s", st_type, binder_info());
|
||||||
|
expr lhs = mk_app(mk_constant(m_mk, st_ls), m_params);
|
||||||
|
for (expr const & field : m_fields) {
|
||||||
|
expr proj = mk_app(mk_app(mk_constant(m_name + mlocal_name(field), st_ls), m_params), st);
|
||||||
|
lhs = mk_app(lhs, proj);
|
||||||
|
}
|
||||||
|
expr eq = mk_app(mk_constant("eq", to_list(sort_level(m_type))), st_type, lhs, st);
|
||||||
|
levels rec_ls = levels(mk_level_zero(), st_ls);
|
||||||
|
expr rec = mk_app(mk_constant(inductive::get_elim_name(m_name), rec_ls), m_params);
|
||||||
|
expr type_former = Fun(st, eq);
|
||||||
|
expr mk = mk_app(mk_app(mk_constant(m_mk, st_ls), m_params), m_fields);
|
||||||
|
expr refl = mk_app(mk_constant(name{"eq", "refl"}, to_list(sort_level(m_type))), st_type, mk);
|
||||||
|
refl = Fun(m_fields, refl);
|
||||||
|
rec = mk_app(rec, type_former, refl, st);
|
||||||
|
expr eta_type = infer_implicit(Pi(m_params, Pi(st, eq)), true);
|
||||||
|
expr eta_value = Fun(m_params, Fun(st, rec));
|
||||||
|
name eta_name(m_name, "eta");
|
||||||
|
|
||||||
|
declaration eta_decl = mk_theorem(eta_name, lnames, eta_type, eta_value);
|
||||||
|
m_env = module::add(m_env, check(m_env, eta_decl));
|
||||||
|
save_thm_info(eta_name);
|
||||||
|
add_alias(eta_name);
|
||||||
|
}
|
||||||
|
|
||||||
environment operator()() {
|
environment operator()() {
|
||||||
process_header();
|
process_header();
|
||||||
m_p.check_token_next(get_assign_tk(), "invalid 'structure', ':=' expected");
|
m_p.check_token_next(get_assign_tk(), "invalid 'structure', ':=' expected");
|
||||||
|
@ -668,6 +703,7 @@ struct structure_cmd_fn {
|
||||||
declare_projections();
|
declare_projections();
|
||||||
declare_auxiliary();
|
declare_auxiliary();
|
||||||
declare_coercions();
|
declare_coercions();
|
||||||
|
declare_eta();
|
||||||
return m_env;
|
return m_env;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
|
@ -1,3 +1,4 @@
|
||||||
add_library(definitional rec_on.cpp induction_on.cpp cases_on.cpp unit.cpp projection.cpp)
|
add_library(definitional rec_on.cpp induction_on.cpp cases_on.cpp unit.cpp eq.cpp
|
||||||
|
projection.cpp)
|
||||||
|
|
||||||
target_link_libraries(definitional ${LEAN_LIBS})
|
target_link_libraries(definitional ${LEAN_LIBS})
|
||||||
|
|
15
tests/lean/run/record4.lean
Normal file
15
tests/lean/run/record4.lean
Normal file
|
@ -0,0 +1,15 @@
|
||||||
|
import logic data.unit
|
||||||
|
|
||||||
|
structure point (A : Type) (B : Type) :=
|
||||||
|
mk :: (x : A) (y : B)
|
||||||
|
|
||||||
|
check point.eta
|
||||||
|
|
||||||
|
example (p : point num num) : point.mk (point.x p) (point.y p) = p :=
|
||||||
|
point.eta p
|
||||||
|
|
||||||
|
inductive color :=
|
||||||
|
red, green, blue
|
||||||
|
|
||||||
|
structure color_point (A : Type) (B : Type) extends point A B :=
|
||||||
|
mk :: (c : color)
|
Loading…
Reference in a new issue