Commit 2025-02-19 07:30 cba55ba8
View on Github →perf: make Decidable Injective
approximately twice as fast (#21975)
The existing implementation takes the definition (∀ x y, f x = f y → x = y
) directly. This is suboptimal because:
- Every pair of values is checked twice (both
(x, y)
and(y, x)
) - The diagonals
(x, x)
are checked redundantly - The outputs of
f
are not cached, which might be a problem iff
is expensive This PR proposes a new implementation ofDecidable Injective
andDecidable InjOn
. It collects the outputs in aMultiset
, then decidesMultiset.Nodup
. BecauseNodup
is built uponList.Pairwise
, which only checks unordered non-diagonal pairs, the above problems are addressed automatically. This also allows for droppingDecidableEq
on the input type, as that was to work around the diagonal case. Thank you @edegeltje and @plp127 for suggestingList.Pairwise
, and many other people in the [Zulip thread] for the discussion aroundSym2
(which ended up being unused here, but was still valuable). [Zulip thread]: https://leanprover.zulipchat.com/#narrow/channel/287929-mathlib4/topic/Idea.3A.20Helper.20for.20speeding.20up.20Decidable.20on.20symmetric.20props