Установить изоморфизм между конечными натуральными числами и сигмой

Я здесь с Coq изучаю отношения между двумя типами, которые я определил. Первый - это что-то вроде конечного подмножества nat, состоящего всего из трех элементов:

Inductive N3 := zero | one | two.

Второй - это сигма-тип с элементами, удовлетворяющими предложению {x: nat | x < 3}. Вот его определение:

Definition less_than_3 := {x| x < 3}.

Я хочу доказать, что эти два типа изоморфны. Я определил две задействованные функции следующим образом:

Definition lt3_to_N3 (n: less_than_3) : N3 :=
match n with
  | exist 0 _ => zero
  | exist 1 _ => one
  | exist 2 _ => two
  | exist _ _ => two
end.

Definition N3_to_lt3 (n: N3) : less_than_3 :=
match n with
  | zero => exist _ 0 l_0_3
  | one => exist _ 1 l_1_3
  | two => exist _ 2 l_2_3
end.

Где l_0_3, l_1_3 и l_2_3 - просто аксиомы:

Axiom l_0_3 : 0 < 3.
Axiom l_1_3 : 1 < 3.
Axiom l_2_3 : 2 < 3.

Мне удается определить первую часть изоморфизма

Definition eq_n3_n3 (n: N3) : lt3_to_N3 (N3_to_lt3 n) = n.
Proof.
by case n.
Defined.

Но я не могу определить другую сторону. Вот что я сделал до сих пор:

Definition eq_lt3_lt3 (x: less_than_3) : eq x (N3_to_lt3 (lt3_to_N3 x)).
Proof.
case: x.
move=> n p.
simpl.
???

Я не совсем уверен в остальном определении. Я также пробовал сопоставить шаблон на x и (N3_to_lt3 (lt3_to_N3 x)), но не уверен, что возвращать.

Definition eq_lt3_lt3 (x: less_than_3) : eq x (N3_to_lt3 (lt3_to_N3 x)) :=
match N3_to_lt3 (lt3_to_N3 x) with
  | x => ???
end.

Спасибо за помощь.


person burionk    schedule 04.08.2017    source источник


Ответы (3)


Я бы начал с чего-то вроде

Definition eq_lt3_lt3 (x: lt3) : eq x (N3_to_lt3 (lt3_to_N3 x)).
Proof.
destruct x as [ n h ].
destruct n as [ | [ | [ | p ]]]; simpl in *.

На этом этапе у вас будут такие цели, как:

exist (fun x : nat => x < 3) 0 h = exist (fun x : nat => x < 3) 0 l_0_3

По сути, единственная разница теперь состоит в том, что у вас есть «некоторое доказательство того, что 0‹ 3 с именем h »слева и« Ваше точное доказательство того, что 0 ‹3 с именем l_0_3» с правой стороны.

Таким образом, вам придется искать в направлении доказательства несоответствия / уникальности удостоверений личности (что можно доказать с помощью nat & lt).

person Vinz    schedule 04.08.2017
comment
Поскольку вы, кажется, используете ssreflect, я помню, что в std lib есть что-то для решения именно этой проблемы, но я не помню точное имя ... - person Vinz; 04.08.2017
comment
Я попытался сделать это, а пока заявить об уникальности как аксиомы: pastebin.com/x3CgPUSH . Доказательство кажется правильным, но в конце концов я оказываюсь в затруднительном положении. Coq просит меня доказать exist (fun x : nat => x < 3) (S (S (S p))) h = exist (fun x : nat => x < 3) 2 l_2_3, но это невозможный случай. Как я могу это решить? - person burionk; 04.08.2017
comment
Разве ваша гипотеза не противоречит? В последнем случае у вас должно быть что-то вроде h : S (S (S p)) < 3. Я почти уверен, что вы знаете, как вывести False для этого оператора;) - person Vinz; 04.08.2017
comment
Что касается уникальности, вы можете взглянуть на le_unique в модуле Peano_dec. - person Vinz; 04.08.2017
comment
Спасибо, наконец-то получил! - person burionk; 04.08.2017

Вы также можете повеселиться, если воспользуетесь механизмом finType в math-comp.

Например, вы можете использовать перечисление ординалов [изоморфных вашему типу], чтобы доказать свою лемму, перечислив все значения вместо громоздких случаев:

From mathcomp Require Import all_ssreflect.

Set Implicit Arguments.
Unset Strict Implicit.
Unset Printing Implicit Defensive.

Lemma falseP T : false -> T.
Proof. by []. Qed.

Inductive N3 := zero | one | two.

Definition lt3_to_N3 (n: 'I_3) : N3 :=
  match n with
  | Ordinal 0 _ => zero
  | Ordinal 1 _ => one
  | Ordinal 2 _ => two
  | Ordinal _ f => falseP _ f
  end.

Definition N3_to_lt3 (n: N3) : 'I_3 :=
  match n with
  | zero => @Ordinal 3 0 erefl
  | one  => @Ordinal 3 1 erefl
  | two  => @Ordinal 3 2 erefl
  end.

Lemma eq_lt3_lt3 : cancel lt3_to_N3 N3_to_lt3.
Proof.
apply/eqfunP; rewrite /FiniteQuant.quant0b /= /pred0b cardE /enum_mem.
by rewrite unlock /= /ord_enum /= !insubT.
Qed.

(* We can define an auxiliary lemma to make our proofs cleaner *)
Lemma all_by_enum (T : finType) (P : pred T) :
  [forall x, P x] = all P (enum T).
Proof.
apply/pred0P/allP => /= H x; first by have/negbFE := H x.
suff Hx : x \in enum T by exact/negbF/H.
by rewrite mem_enum.
Qed.

Lemma eq_lt3_lt3' : cancel lt3_to_N3 N3_to_lt3.
Proof.
by apply/eqfunP; rewrite all_by_enum enumT unlock /= /ord_enum /= !insubT.
Qed.

Как видите, текущий дизайн math-comp не очень хорошо подходит для этой работы, но, тем не менее, интересно познакомиться с библиотекой побольше.

Еще одно интересное упражнение - определить экземпляр finType для вашего пользовательского типа данных, а затем установить, что оба набора имеют одинаковую мощность! Есть много комбинаций лемм, которые можно попробовать здесь, так что вам будет весело!

person ejgallego    schedule 06.08.2017
comment
Это кажется немного более сложным. Я постараюсь пройти через ваше доказательство, спасибо! - person burionk; 07.08.2017

Поскольку вы используете ssreflect, самый простой способ - использовать вычислительное определение <ssrnat), а затем применить лемму val_inj:

From mathcomp Require Import ssreflect ssrfun ssrbool eqtype ssrnat.

Inductive N3 := zero | one | two.

Definition less_than_3 := {x| x < 3}.

Definition lt3_to_N3 (n: less_than_3) : N3 :=
match n with
  | exist 0 _ => zero
  | exist 1 _ => one
  | exist 2 _ => two
  | exist _ _ => two
end.

Definition N3_to_lt3 (n: N3) : less_than_3 :=
match n with
  | zero => exist _ 0 erefl
  | one => exist _ 1 erefl
  | two => exist _ 2 erefl
end.

Lemma eq_lt3_lt3 (x: less_than_3) : eq x (N3_to_lt3 (lt3_to_N3 x)).
Proof.
by apply: val_inj; case: x => [[| [|[|x]]] Px].
Qed.

Оператор val_inj немного сложен, но основная идея проста: для любого логического предиката P типа T каноническая проекция { x : T | P x = true } -> T инъективна. Как выразился Винц, это полагается на то, что логические равенства не имеют отношения к доказательству; то есть любые два доказательства равенства между логическими значениями сами равны. По этой причине равенство на {x | P x = true} полностью определяется элементом x; компонент доказательства не имеет значения.

person Arthur Azevedo De Amorim    schedule 04.08.2017
comment
Я предлагаю использовать определение bijective в ssrflect, которое, в свою очередь, зависит от cancel. - person ejgallego; 06.08.2017