module Fin where import Relation.Binary.PropositionalEquality as Eq open Eq using (_≡_; refl; _≢_; sym; trans; subst; cong) open Eq.≡-Reasoning open import Data.Nat using (ℕ; zero; suc; _+_; _≤_; s≤s; z≤n; _<_; _⊓_) open import Data.Nat.Properties -- don't use the library version of ≤-<-connex -- use m≤n⇒m≤1+n instead of ≤-step using (suc-injective; ≤-reflexive; ≤-refl; ≤-trans; <-irrefl; <⇒≤; m≤n⇒m≤1+n; <-transˡ; <-transʳ; ≤∧≢⇒<; +-monoˡ-<; m≤m+n; m≤n+m; m≤n⇒m≤o+n; +-mono-≤; m<n⇒m⊓o<n; m≤n⇒m⊓n≡m; ⊓-comm; -- ≤-total; m⊓n≤m) open import Data.Product using (Σ; _×_; _,_; proj₁; proj₂ ; ∃; Σ-syntax; ∃-syntax; ∃₂) open import Data.Sum using (_⊎_; inj₁; inj₂) renaming ([_,_]′ to case-⊎) open import Relation.Nullary using (¬_; Dec; yes; no) open import Data.Unit using (⊤; tt) open import Data.Empty using (⊥; ⊥-elim) open import Relation.Unary using (_∈_; Satisfiable) open import Function using (_∘_; id) open import Data.List using (List; []; _∷_; _++_; length; sum; _ʳ++_) import Data.Fin as F open F using (Fin; toℕ; fromℕ<) open import Data.Fin.Properties using (pigeonhole; toℕ-mono-<; toℕ<n; fromℕ<-toℕ; fromℕ<-cong; toℕ-fromℕ<; toℕ-injective; fromℕ<-injective) open import Data.Maybe using (Maybe; just; nothing) open import Data.Maybe.Properties using (just-injective) open import Relation.Binary.Core using (_⇒_) open import Miscellaneous -- open import Classical open import WQO -- open import MinimalBadSeq -- import Higman as H private variable A : Set n : ℕEquality is a WQO on Fin n.
module Fin-≡ where almostFull : {n : ℕ} → AlmostFull {Fin n} _≡_ almostFull {n} f = toℕ i , toℕ j , toℕ-mono-< i<j , g[i]≡g[j] -- toℕ-mono-< i<j is not in stdlib 1.7.2 where g : Fin (suc n) → Fin n g = f ∘ toℕ [1] : ∃₂ (λ i j → i F.< j × g i ≡ g j) -- i ≢ j instead of i < j in stdlib 1.7.1 [1] = pigeonhole ≤-refl g i = proj₁ [1] j = proj₁ (proj₂ [1]) i<j : i F.< j i<j = proj₁ (proj₂ (proj₂ [1])) g[i]≡g[j] : g i ≡ g j g[i]≡g[j] = proj₂ (proj₂ (proj₂ [1])) isWQO : (n : ℕ) → IsWQO {A = Fin n} _≡_ isWQO n = record { isQO = record { reflexive = refl ; transitive = trans } ; almostFull = almostFull }Define inequality on Maybe (Fin n) so that nothing is the bottom element. Equality on Maybe (Fin n) is almost full.
module _ {n : ℕ} where _≤′_ : Maybe (Fin n) → Maybe (Fin n) → Set just i ≤′ just j = i F.≤ j just _ ≤′ nothing = ⊥ nothing ≤′ _ = ⊤ -- nothing ≤′ just _ = ⊤ -- nothing ≤′ nothing = ⊤ ≤′-refl : Reflexive _≤′_ ≤′-refl {x = just x} = ≤-refl ≤′-refl {x = nothing} = tt ≤′-reflexive : _≡_ ⇒ _≤′_ ≤′-reflexive refl = ≤′-refl ≤′-trans : Transitive _≤′_ ≤′-trans {x = just x} {y = just y} {z = just z} xy yz = ≤-trans xy yz ≤′-trans {x = nothing} {y = just y} {z = just z} xy yz = tt ≤′-trans {x = nothing} {y = nothing} {z = just z} xy yz = tt ≤′-trans {x = nothing} {y = nothing} {z = nothing} xy yz = tt ≤′-just-just : (i : Fin n) (m : Maybe (Fin n)) → just i ≤′ m → ∃[ j ] m ≡ just j ≤′-just-just i (just j) h = j , refl
Funny minimum operator on Fin n. This will be used in the definition of min below.
_⊓′_ : Maybe (Fin n) → Maybe (Fin n) → Maybe (Fin n) just i ⊓′ just j = just (fromℕ< (m<n⇒m⊓o<n (toℕ j) (toℕ<n i))) just i ⊓′ nothing = just i nothing ⊓′ just j = just j nothing ⊓′ nothing = nothing ⊓′-⊓ : (i j : Fin n) → ∃[ k ] (just i ⊓′ just j) ≡ just k × toℕ k ≡ toℕ i ⊓ toℕ j ⊓′-⊓ i j = (fromℕ< (m<n⇒m⊓o<n (toℕ j) (toℕ<n i))) , refl , toℕ-fromℕ< ((m<n⇒m⊓o<n (toℕ j) (toℕ<n i))) ⊓′-comm : (x y : Maybe (Fin n)) → x ⊓′ y ≡ y ⊓′ x -- ⊓′-comm (just i) (just j) = cong just (fromℕ<-cong (toℕ i ⊓ toℕ j) (toℕ j ⊓ toℕ i) (⊓-comm (toℕ i) (toℕ j)) (m<n⇒m⊓o<n (toℕ j) (toℕ<n i)) (m<n⇒m⊓o<n (toℕ i) (toℕ<n j))) ⊓′-comm (just i) (just j) with ⊓′-⊓ i j | ⊓′-⊓ j i ... | k , eq₁ , eq₂ | l , eq₃ , eq₄ = trans eq₁ (trans (cong just [3]) (sym eq₃)) where [1] : toℕ k ≡ toℕ j ⊓ toℕ i [1] = trans eq₂ (⊓-comm (toℕ i) (toℕ j)) [2] : toℕ k ≡ toℕ l [2] = trans [1] (sym eq₄) [3] : k ≡ l [3] = toℕ-injective [2] ⊓′-comm (just i) nothing = refl ⊓′-comm nothing (just j) = refl ⊓′-comm nothing nothing = refl ≤-⊓′ : {i j : Fin n} → toℕ i ≤ toℕ j → just i ⊓′ just j ≡ just i ≤-⊓′ {i} {j} i≤j = [4] where [1] : toℕ i ⊓ toℕ j ≡ toℕ i [1] = m≤n⇒m⊓n≡m i≤j [2] : fromℕ< (toℕ<n i) ≡ i [2] = fromℕ<-toℕ i (toℕ<n i) [3] : fromℕ< (m<n⇒m⊓o<n (toℕ j) (toℕ<n i)) ≡ i [3] = trans (fromℕ<-cong (toℕ i ⊓ toℕ j) (toℕ i) [1] (m<n⇒m⊓o<n (toℕ j) (toℕ<n i)) (toℕ<n i)) (fromℕ<-toℕ i (toℕ<n i)) [4] : just i ⊓′ just j ≡ just i [4] = cong just [3] ≥-⊓′ : {i j : Fin n} → toℕ j ≤ toℕ i → just i ⊓′ just j ≡ just j ≥-⊓′ {i} {j} j≤i = trans (⊓′-comm (just i) (just j)) (≤-⊓′ j≤i) ⊓′-≤′₁ : (i j : Fin n) → (just i ⊓′ just j) ≤′ just i ⊓′-≤′₁ i j with ⊓′-⊓ i j ... | k , eq₁ , eq₂ = [3] where [1] : toℕ k ≤ toℕ i [1] rewrite eq₂ = m⊓n≤m (toℕ i) (toℕ j) [2] : just k ≤′ just i [2] = [1] [3] : (just i ⊓′ just j) ≤′ just i [3] = subst (_≤′ just i) (sym eq₁) [2] ⊓′-≤′₂ : (i j : Fin n) → (just i ⊓′ just j) ≤′ just j ⊓′-≤′₂ i j = subst (_≤′ just j) (⊓′-comm (just j) (just i)) (⊓′-≤′₁ j i) ⊓′-≤′₃ : (i : Fin n) (m : Maybe (Fin n)) → (just i ⊓′ m) ≤′ just i ⊓′-≤′₃ i (just j) = ⊓′-≤′₁ i j ⊓′-≤′₃ i nothing = ≤-refl ⊓′-≤′₄ : (m : Maybe (Fin n)) (j : Fin n) → (m ⊓′ just j) ≤′ just j ⊓′-≤′₄ (just i) j = ⊓′-≤′₂ i j ⊓′-≤′₄ nothing j = ≤-refl ⊓′-nothing₁ : (m₁ m₂ : Maybe (Fin n)) → (m₁ ⊓′ m₂) ≡ nothing → m₁ ≡ nothing ⊓′-nothing₁ (just i) (just j) () ⊓′-nothing₁ (just i) nothing () ⊓′-nothing₁ nothing (just j) () ⊓′-nothing₁ nothing nothing refl = refl ⊓′-nothing₂ : (m₁ m₂ : Maybe (Fin n)) → (m₁ ⊓′ m₂) ≡ nothing → m₂ ≡ nothing ⊓′-nothing₂ (just i) (just j) () ⊓′-nothing₂ (just i) nothing () ⊓′-nothing₂ nothing (just j) () ⊓′-nothing₂ nothing nothing refl = refl ⊓′-nothing-just : (m : Maybe (Fin n)) (i : Fin n) → (nothing ⊓′ m) ≡ just i → m ≡ just i ⊓′-nothing-just (just i) .i refl = refl module MaybeFin-≡ {n : ℕ} where open M {Fin n} _≡_ ≡-≼′ : (x y : Maybe (Fin n)) → (x ≡ y) ⇔ (x ≼′ y) ≡-≼′ (just x) (just y) = (λ {refl → refl}) , (λ {refl → refl}) ≡-≼′ (just x) nothing = (λ {()}) , λ {()} ≡-≼′ nothing (just y) = (λ {()}) , λ {()} ≡-≼′ nothing nothing = (λ {refl → tt}) , λ _ → refl almostFull : AlmostFull {Maybe (Fin n)} _≡_ almostFull f with maybe-almostFull Fin-≡.almostFull f ... | i , j , i<j , h = i , j , i<j , proj₂ (≡-≼′ (f i) (f j)) h