lean4-htt/tests/lean/inaccessible.lean
Leonardo de Moura 90bfd84a07 feat(frontends/lean): Type is now (Type 1)
In the standard library, we should use explicit universe variables for
universe polymorphic definitions.

Users that want to declare universe polymorphic definitions but do not
want to provide universe level parameters should use
  Type _
or
  Type*
2016-09-17 14:30:54 -07:00

83 lines
3.3 KiB
Text

universe variables u v
inductive imf {A : Type u} {B : Type v} (f : A → B) : B → Type (max 1 u v)
| mk : ∀ (a : A), imf (f a)
definition inv_1 {A : Type u} {B : Type v} (f : A → B) : ∀ (b : B), imf f b → A
| .(f a) (imf.mk .f a) := a
definition inv_2 {A : Type u} {B : Type v} (f : A → B) : ∀ (b : B), imf f b → A
| ._ (imf.mk ._ a) := a
definition mk {A : Type u} {B : Type v} {f : A → B} (a : A) := imf.mk f a
definition inv_3 {A : Type u} {B : Type v} (f : A → B) : ∀ (b : B), imf f b → A
| .(f a) (mk a) := a -- Error, mk is not a constructor
definition inv_4 {A : Type u} {B : Type v} (f : A → B) : ∀ (b : B), imf f b → A
| .(f a) (.mk a) := a -- Error, we cannot use inaccessible annotation around functions in applications
attribute [pattern] mk
definition inv_5 {A : Type u} {B : Type v} (f : A → B) : ∀ (b : B), imf f b → A
| .(f a) (mk a) := a
definition inv_6 {A : Type u} {B : Type v} (f : A → B) : ∀ (b : B), imf f b → A
| (f a) (mk a) := a -- Error, 'a' is being "declared" twice in the pattern
definition inv_7 {A : Type u} {B : Type v} (f : A → B) : ∀ (b : B), imf f b → A
| (f a) (mk b) := a -- Typing error, it would also fail when compiling the pattern
definition g_1 : nat → nat → nat
| a a := a -- Error, 'a' is being "declared" twice
definition g_2 (a : nat) : nat → nat → nat
| a b := a
example (a b c : nat) : g_2 a b c = b :=
rfl
inductive vec1 (A : Type u) : nat → Type (max 1 u)
| nil : vec1 0
| cons : ∀ n, A → vec1 n → vec1 (n+1)
section
open vec1
definition map_1 {A : Type u} (f : A → A → A) : Π {n}, vec1 A n → vec1 A n → vec1 A n
| 0 (nil .A) (nil .A) := nil A
| (n+1) (cons .n h₁ v₁) (cons .n h₂ v₂) := cons n (f h₁ h₂) (map_1 v₁ v₂)
definition map_2 {A : Type u} (f : A → A → A) : Π {n}, vec1 A n → vec1 A n → vec1 A n
| 0 (nil ._) (nil ._) := nil A
| (n+1) (cons ._ h₁ v₁) (cons ._ h₂ v₂) := cons n (f h₁ h₂) (map_2 v₁ v₂)
/- In map_3, we use the inaccessible terms to avoid pattern/matching on the first argument -/
definition map_3 {A : Type u} (f : A → A → A) : Π {n}, vec1 A n → vec1 A n → vec1 A n
| ._ (nil ._) (nil ._) := nil A
| ._ (cons n h₁ v₁) (cons .n h₂ v₂) := cons n (f h₁ h₂) (map_3 v₁ v₂)
end
inductive vec2 (A : Type u) : nat → Type (max 1 u)
| nil {} : vec2 0
| cons : ∀ {n}, A → vec2 n → vec2 (n+1)
section
open vec2
definition map_4 {A : Type u} (f : A → A → A) : Π {n}, vec2 A n → vec2 A n → vec2 A n
| 0 nil nil := nil
| (n+1) (cons h₁ v₁) (cons h₂ v₂) := cons (f h₁ h₂) (map_4 v₁ v₂)
definition map_5 {A : Type u} (f : A → A → A) : Π {n}, vec2 A n → vec2 A n → vec2 A n
| ._ nil nil := nil
| ._ (@cons .A n h₁ v₁) (cons h₂ v₂) := cons (f h₁ h₂) (map_5 v₁ v₂)
/-
The following variant will be rejected by the new equation compiler.
In Lean2, the second equation is accepted because unassigned metavariables
occurring in patterns become new variables. This feature is too hackish.
-/
definition map_6 {A : Type u} (f : A → A → A) : Π {n}, vec2 A n → vec2 A n → vec2 A n
| ._ nil nil := nil
| ._ (cons h₁ v₁) (cons h₂ v₂) := cons (f h₁ h₂) (map_6 v₁ v₂)
end