|
| 1 | +/- |
| 2 | +Copyright (c) 2021 Peter Nelson. All rights reserved. |
| 3 | +Released under Apache 2.0 license as described in the file LICENSE. |
| 4 | +Authors: Peter Nelson |
| 5 | +-/ |
| 6 | +import data.fintype.basic |
| 7 | + |
| 8 | +/-! |
| 9 | +# Order structures on finite types |
| 10 | +
|
| 11 | +This file provides order instances on fintypes: |
| 12 | +* A `semilattice_inf` instance on a `fintype` allows constructing an `order_bot`. |
| 13 | +* A `semilattice_sup` instance on a `fintype` allows constructing an `order_top`. |
| 14 | +* A `lattice` instance on a `fintype` allows constructing a `bounded_order`. |
| 15 | +* A `lattice` instance on a `fintype` can be promoted to a `complete_lattice`. |
| 16 | +* A `linear_order` instance on a `fintype` can be promoted to a `complete_linear_order`. |
| 17 | +
|
| 18 | +Getting to a `bounded_order` from a `lattice` is computable, but the |
| 19 | +subsequent definitions are not, since the definitions of `Sup` and `Inf` use `set.to_finset`, which |
| 20 | +implicitly requires a `decidable_pred` instance for every `s : set α`. |
| 21 | +
|
| 22 | +The `complete_linear_order` instance for `fin (n + 1)` is the only proper instance in this file. The |
| 23 | +rest are `def`s to avoid loops in typeclass inference. |
| 24 | +-/ |
| 25 | + |
| 26 | +variables {ι α : Type*} [fintype ι] [fintype α] |
| 27 | + |
| 28 | +section inhabited |
| 29 | +variables (α) [inhabited α] |
| 30 | + |
| 31 | +/-- Constructs the `⊥` of a finite inhabited `semilattice_inf`. -/ |
| 32 | +@[reducible] -- See note [reducible non-instances] |
| 33 | +def fintype.to_order_bot [semilattice_inf α] : order_bot α := |
| 34 | +{ bot := finset.fold (⊓) (arbitrary α) id finset.univ, |
| 35 | + bot_le := λ a, ((finset.fold_op_rel_iff_and (@le_inf_iff α _)).1 le_rfl).2 a (finset.mem_univ _) } |
| 36 | + |
| 37 | +/-- Constructs the `⊤` of a finite inhabited `semilattice_sup` -/ |
| 38 | +@[reducible] -- See note [reducible non-instances] |
| 39 | +def fintype.to_order_top [semilattice_sup α] : order_top α := |
| 40 | +{ top := finset.fold (⊔) (arbitrary α) id finset.univ, |
| 41 | + le_top := λ a, |
| 42 | + ((finset.fold_op_rel_iff_and (λ x y z, show x ≥ y ⊔ z ↔ _, from sup_le_iff)).mp le_rfl).2 |
| 43 | + a (finset.mem_univ a) } |
| 44 | + |
| 45 | +/-- Constructs the `⊤` and `⊥` of a finite inhabited `lattice`. -/ |
| 46 | +@[reducible] -- See note [reducible non-instances] |
| 47 | +def fintype.to_bounded_order [lattice α] : bounded_order α := |
| 48 | +{ .. fintype.to_order_bot α, |
| 49 | + .. fintype.to_order_top α } |
| 50 | + |
| 51 | +end inhabited |
| 52 | + |
| 53 | +section bounded_order |
| 54 | +variables (α) |
| 55 | + |
| 56 | +open_locale classical |
| 57 | + |
| 58 | +/-- A finite bounded lattice is complete. -/ |
| 59 | +@[reducible] -- See note [reducible non-instances] |
| 60 | +noncomputable def fintype.to_complete_lattice [hl : lattice α] [hb : bounded_order α] : |
| 61 | + complete_lattice α := |
| 62 | +{ Sup := λ s, s.to_finset.sup id, |
| 63 | + Inf := λ s, s.to_finset.inf id, |
| 64 | + le_Sup := λ _ _ ha, finset.le_sup (set.mem_to_finset.mpr ha), |
| 65 | + Sup_le := λ s _ ha, finset.sup_le (λ b hb, ha _ $ set.mem_to_finset.mp hb), |
| 66 | + Inf_le := λ _ _ ha, finset.inf_le (set.mem_to_finset.mpr ha), |
| 67 | + le_Inf := λ s _ ha, finset.le_inf (λ b hb, ha _ $ set.mem_to_finset.mp hb), |
| 68 | + .. hl, .. hb } |
| 69 | + |
| 70 | +/-- A finite bounded linear order is complete. -/ |
| 71 | +@[reducible] -- See note [reducible non-instances] |
| 72 | +noncomputable def fintype.to_complete_linear_order [h : linear_order α] [bounded_order α] : |
| 73 | + complete_linear_order α := |
| 74 | +{ .. fintype.to_complete_lattice α, .. h } |
| 75 | + |
| 76 | +end bounded_order |
| 77 | + |
| 78 | +section nonempty |
| 79 | +variables (α) [nonempty α] |
| 80 | + |
| 81 | +/-- A nonempty finite lattice is complete. If the lattice is already a `bounded_order`, then use |
| 82 | +`fintype.to_complete_lattice` instead, as this gives definitional equality for `⊥` and `⊤`. -/ |
| 83 | +@[reducible] -- See note [reducible non-instances] |
| 84 | +noncomputable def fintype.to_complete_lattice_of_lattice [lattice α] : complete_lattice α := |
| 85 | +@fintype.to_complete_lattice _ _ _ $ @fintype.to_bounded_order α _ ⟨classical.arbitrary α⟩ _ |
| 86 | + |
| 87 | +/-- A nonempty finite linear order is complete. If the linear order is already a `bounded_order`, |
| 88 | +then use `fintype.to_complete_linear_order` instead, as this gives definitional equality for `⊥` and |
| 89 | +`⊤`. -/ |
| 90 | +@[reducible] -- See note [reducible non-instances] |
| 91 | +noncomputable def fintype.to_complete_linear_order_of_linear_order [h : linear_order α] : |
| 92 | + complete_linear_order α := |
| 93 | +{ .. fintype.to_complete_lattice_of_lattice α, |
| 94 | + .. h } |
| 95 | + |
| 96 | +end nonempty |
| 97 | + |
| 98 | +/-! ### `fin` -/ |
| 99 | + |
| 100 | +noncomputable instance fin.complete_linear_order {n : ℕ} : complete_linear_order (fin (n + 1)) := |
| 101 | +fintype.to_complete_linear_order _ |
0 commit comments