Zulip Chat Archive
Stream: general
Topic: cardinals of finite sets
Mario Carneiro (Aug 18 2018 at 05:19):
People have mentioned that working with the size of finite sets is a bit complicated right now. We have two methods to talk about the cardinality of a type:
fintype.card A
, which requires a[fintype A]
instance (and hence asserts cardinality separately from finiteness), andcardinal.mk A
, which works on any type but has typecardinal
instead ofnat
(which makes it useful for different sizes of infinite sets).
In order to use this latter expression to assert a set has a finite number cardinality you have to write cardinal.mk A = ↑n
where n : nat
, which is a bit messy, since cardinal.mk A = 37
is not the same as cardinal.mk A = ↑37
(you can use simp
to turn one into the other).
I would like to make it easy to talk about finite sets with natural number cardinalities, without having finiteness as a precondition. Some options:
has_card A n
is{ x : fintype A // card A x = n }
. This has the advantage that it is computable, and a subsingleton, although it is not a proposition stated this way. Since it is a relation rather than a function, you can't rewrite with it, but whether this is a problem depends on how it is used.card_xnat A : with_top nat
is a noncomputable function that takes the value⊤
on infinite sets andn
on finite sets of cardinalityn
. Here we can state lemmas likecard_xnat (sum A B) = card_xnat A + card_xnat B
without preconditions, and prove equality with other kinds of cardinality to relate back to the computable versions.card_nat A : nat
is the same ascard_xnat
but with a 0 default value instead of⊤
. This is really just a totalized partial function, so many theorems will not hold without finiteness assumptions, but it has the advantage that it takes values innat
so you get the same experience asfintype.card A
but without the dependent argument, which can sometimes mess up rewrites.
Johannes Hölzl (Aug 18 2018 at 10:50):
I'm currently finishing ennreal := with_top nnreal
. The setup should work also for nat
, then card_xnat
(maybe named card_enat
, c.f. ennreal
) would work nice, as it goes into a complete lattice.
Chris Hughes (Aug 18 2018 at 11:15):
What's the solution used on Coq? Presumably they must have dealt with this a lot to prove Feit Thompson.
Mario Carneiro (Aug 18 2018 at 11:26):
feit thompson dealt almost exclusively in finite group theory
Mario Carneiro (Aug 18 2018 at 11:26):
so it wasn't a problem to have finiteness assumptions everywhere
Mario Carneiro (Aug 18 2018 at 11:27):
plus ssreflect has a lot of slightly different approaches to all this stuff which emphasizes bool
predicates over propositions
Mario Carneiro (Aug 18 2018 at 11:28):
Metamath has a #
function which is essentially card_enat
; it has a range which is a subset of ennreal (of course they don't deal with subtypes like we do here)
Mario Carneiro (Aug 18 2018 at 11:29):
but you could say basically #({A, B, C}) = 3
where that is the usual 3
Mario Carneiro (Aug 18 2018 at 11:30):
and this was a distinct function from card : V -> On
which takes values in the ordinals (and defines the cardinals as the range of this function)
Mario Carneiro (Aug 18 2018 at 11:32):
I think that in general the classical mathematics approach used in lean makes it resemble Isabelle and Metamath a lot more than Coq
Chris Hughes (Aug 30 2018 at 20:28):
May I suggest another option. If we're going down the noncomputable route and the having two different definitions route, I think the best solution is to have a finite
predicate to use instead of fintype
. This has the advantage of solving the rw
issue, which also indirectly helps the type class inference issue, because theorems like card_empty
wouldn't need fintype empty
as an input, which makes the type class inference issue easier as well.
All of these options seem wrong to me however, and I'd much rather not confuse people even more by introducing a fourth way of talking about finite cardinals.
Kenny Lau (Aug 30 2018 at 20:29):
what is your fourth way?
Chris Hughes (Aug 30 2018 at 20:31):
Making a finite
predicate instead of fintype
which is Type
Johannes Hölzl (Aug 31 2018 at 07:20):
We have already set.finite
. It was defined as inductive over empty and insert, currently it is defined by saying that the set coerced to a type is a fintype
.
Last updated: Dec 20 2023 at 11:08 UTC