A computable model of ZFA without infinity #
In this file we define finite hereditary lists. This is useful for calculations in naive set theory.
We distinguish two kinds of ZFA lists:
- Atoms. Directly correspond to an element of the original type.
- Proper ZFA lists. Can be thought of (but aren't implemented) as a list of ZFA lists (not necessarily proper).
For example, Lists ℕ
contains stuff like 23
, []
, [37]
, [1, [[2], 3], 4]
.
Implementation note #
As we want to be able to append both atoms and proper ZFA lists to proper ZFA lists, it's handy that
atoms and proper ZFA lists belong to the same type, even though atoms of α
could be modelled as
α
directly. But we don't want to be able to append anything to atoms.
This calls for a two-steps definition of ZFA lists:
- First, define ZFA prelists as atoms and proper ZFA prelists. Those proper ZFA prelists are defined by inductive appending of (not necessarily proper) ZFA lists.
- Second, define ZFA lists by rubbing out the distinction between atoms and proper lists.
Main declarations #
Lists' α false
: Atoms as ZFA prelists. Basically a copy ofα
.Lists' α true
: Proper ZFA prelists. Defined inductively from the empty ZFA prelist (Lists'.nil
) and from appending a ZFA prelist to a proper ZFA prelist (Lists'.cons a l
).Lists α
: ZFA lists. Sum of the atoms and proper ZFA prelists.Finsets α
: ZFA sets. Defined asLists
quotiented byLists.Equiv
, the extensional equivalence.
Prelists, helper type to define Lists
. Lists' α false
are the "atoms", a copy of α
.
Lists' α true
are the "proper" ZFA prelists, inductively defined from the empty ZFA prelist and
from appending a ZFA prelist to a proper ZFA prelist. It is made so that you can't append anything
to an atom while having only one appending function for appending both atoms and proper ZFC prelists
to a proper ZFA prelist.
- atom: {α : Type u} → α → Lists' α false
- nil: {α : Type u} → Lists' α true
- cons': {α : Type u} → {b : Bool} → Lists' α b → Lists' α true → Lists' α true
Instances For
Equations
- instDecidableEqLists' = decEqLists'✝
Hereditarily finite list, aka ZFA list. A ZFA list is either an "atom" (b = false
),
corresponding to an element of α
, or a "proper" ZFA list, inductively defined from the empty ZFA
list and from appending a ZFA list to a proper ZFA list.
Instances For
Equations
- Lists'.instForAllBoolInhabitedLists' x = match x with | true => { default := Lists'.nil } | false => { default := Lists'.atom default }
Appending a ZFA list to a proper ZFA prelist.
Equations
- Lists'.cons x✝ x = match x✝, x with | { fst := fst, snd := a }, l => Lists'.cons' a l
Instances For
Converts a ZFA prelist to a List
of ZFA lists. Atoms are sent to []
.
Equations
- Lists'.toList (Lists'.atom a) = []
- Lists'.toList Lists'.nil = []
- Lists'.toList (Lists'.cons' a l) = { fst := b, snd := a } :: Lists'.toList l
Instances For
Converts a List
of ZFA lists to a proper ZFA prelist.
Equations
- Lists'.ofList [] = Lists'.nil
- Lists'.ofList (a :: l) = Lists'.cons a (Lists'.ofList l)
Instances For
Equivalence of ZFA lists. Defined inductively.
- refl: ∀ {α : Type u_1} (l : Lists α), Lists.Equiv l l
- antisymm: ∀ {α : Type u_1} {l₁ l₂ : Lists' α true}, Lists'.Subset l₁ l₂ → Lists'.Subset l₂ l₁ → Lists.Equiv { fst := true, snd := l₁ } { fst := true, snd := l₂ }
Instances For
Subset relation for ZFA lists. Defined inductively.
- nil: ∀ {α : Type u_1} {l : Lists' α true}, Lists'.Subset Lists'.nil l
- cons: ∀ {α : Type u_1} {a a' : Lists α} {l l' : Lists' α true}, Lists.Equiv a a' → a' ∈ Lists'.toList l' → Lists'.Subset l l' → Lists'.Subset (Lists'.cons a l) l'
Instances For
ZFA prelist membership. A ZFA list is in a ZFA prelist if some element of this ZFA prelist is equivalent as a ZFA list to this ZFA list.
Equations
- Lists'.instMembershipListsLists' = { mem := fun (a : Lists α) (l : Lists' α b) => ∃ (a' : Lists α), a' ∈ Lists'.toList l ∧ Lists.Equiv a a' }
Sends a : α
to the corresponding atom in Lists α
.
Equations
- Lists.atom a = { fst := false, snd := Lists'.atom a }
Instances For
Converts a ZFA list to a List
of ZFA lists. Atoms are sent to []
.
Equations
- Lists.toList x = match x with | { fst := fst, snd := l } => Lists'.toList l
Instances For
Converts a List
of ZFA lists to a ZFA list.
Equations
- Lists.ofList l = Lists.of' (Lists'.ofList l)
Instances For
A recursion principle for pairs of ZFA lists and proper ZFA prelists.
Equations
- One or more equations did not get rendered due to their size.
Instances For
Membership of ZFA list. A ZFA list belongs to a proper ZFA list if it belongs to the latter as a proper ZFA prelist. An atom has no members.
Equations
Instances For
Equations
- Lists.instMembershipLists = { mem := Lists.mem }
Equations
- Lists.instSetoidLists = { r := fun (x x_1 : Lists α) => Lists.Equiv x x_1, iseqv := (_ : Equivalence fun (x x_1 : Lists α) => Lists.Equiv x x_1) }
Auxiliary function to prove termination of decidability checking
Equations
- One or more equations did not get rendered due to their size.
Instances For
Equations
- Lists.Equiv.decidable { fst := false, snd := l₁ } { fst := false, snd := l₂ } = decidable_of_iff' (l₁ = l₂) (_ : Lists.Equiv { fst := false, snd := l₁ } { fst := false, snd := l₂ } ↔ l₁ = l₂)
- Lists.Equiv.decidable { fst := false, snd := l₁ } { fst := true, snd := l₂ } = isFalse (_ : Lists.Equiv { fst := false, snd := l₁ } { fst := true, snd := l₂ } → False)
- Lists.Equiv.decidable { fst := true, snd := l₁ } { fst := false, snd := l₂ } = isFalse (_ : Lists.Equiv { fst := true, snd := l₁ } { fst := false, snd := l₂ } → False)
- Lists.Equiv.decidable { fst := true, snd := l₁ } { fst := true, snd := l₂ } = decidable_of_iff' (l₁ ⊆ l₂ ∧ l₂ ⊆ l₁) (_ : Lists.Equiv (Lists.of' l₁) (Lists.of' l₂) ↔ l₁ ⊆ l₂ ∧ l₂ ⊆ l₁)
Equations
- Lists.Subset.decidable Lists'.nil x = isTrue (_ : Lists'.Subset Lists'.nil x)
- Lists.Subset.decidable (Lists'.cons' a l₁) x = decidable_of_iff' ({ fst := b, snd := a } ∈ x ∧ l₁ ⊆ x) (_ : Lists'.cons { fst := b, snd := a } l₁ ⊆ x ↔ { fst := b, snd := a } ∈ x ∧ l₁ ⊆ x)
Equations
- Lists.mem.decidable x Lists'.nil = isFalse (_ : x ∈ Lists'.nil → False)
- Lists.mem.decidable x (Lists'.cons' b_1 l₂) = decidable_of_iff' (Lists.Equiv x { fst := b, snd := b_1 } ∨ x ∈ l₂) (_ : x ∈ Lists'.cons' b_1 l₂ ↔ Lists.Equiv x { fst := b, snd := b_1 } ∨ x ∈ l₂)