Zulip Chat Archive
Stream: lean4
Topic: Lean.Expr.proj
Arthur Paulino (May 30 2022 at 13:31):
In the metaprogramming book, @Edward Ayers described this constructor as:
proj
is for projection. Suppose you have a structure such asp : α × β
,
rather than storing the projectionπ₁ p
asapp π₁ p
, it is expressed as
proj Prod 0 p
. This is for efficiency reasons
Is this documented somewhere? Where can I learn more about it? Thanks in advance!
Mario Carneiro (May 30 2022 at 13:41):
well, you are talking about the very book that would be the documentation, so not really
Mario Carneiro (May 30 2022 at 13:41):
is there something in particular you want to know about it?
Mario Carneiro (May 30 2022 at 13:42):
They are called "primitive projections" and they correspond to the fields of a structure
Arthur Paulino (May 30 2022 at 13:43):
Hm, is there anything we lose (but efficiency) if we face them as regular applications? Like some expressiveness power
Mario Carneiro (May 30 2022 at 13:59):
no, it's just for efficiency
Mario Carneiro (May 30 2022 at 14:00):
they are not supposed to be an extension to the logic, they just abbreviate applications of the recursor
Mario Carneiro (May 30 2022 at 14:00):
nat and string literals are the same way
Arthur Paulino (May 30 2022 at 14:06):
Alright, thanks!
Arthur Paulino (Jun 01 2022 at 04:35):
How can I make it print proj
?
import Lean
open Lean Elab Command Term in
elab "#inspect" t:term : command => do
liftTermElabM `inspect do
let t ← elabTerm t none
synthesizeSyntheticMVarsNoPostponing
dbg_trace t.ctorName
structure Foo where
aa : Nat
bb : String
#inspect (Foo.mk 1 "hi").1 -- app
#inspect (Foo.mk 1 "hi").aa -- app
#inspect (1, 2).1 -- app
#inspect (1, 2).fst -- app
Mario Carneiro (Jun 01 2022 at 05:12):
Not easily. proj
is generally not supposed to show up in normal terms. But you can look at the implementation of the projections to find occurrences of proj
:
import Lean
elab "#inspect" t:ident : command => do
if let some ci := (← Lean.getEnv).find? t.getId then
dbg_trace repr ci.value!
structure Foo where
aa : Nat
bb : String
#inspect Foo.aa
-- Lean.Expr.lam
-- `self
-- (Lean.Expr.const `Foo [] (Expr.mkData 1485976967 (bi := Lean.BinderInfo.default)))
-- (Lean.Expr.proj
-- `Foo
-- 0
-- (Lean.Expr.bvar 0 (Expr.mkData 4279369707 (looseBVarRange := 1) (bi := Lean.BinderInfo.default)))
-- (Expr.mkData 1237988559 (looseBVarRange := 1) (approxDepth := 1) (bi := Lean.BinderInfo.default)))
-- (Expr.mkData 3385561612 (approxDepth := 2) (bi := Lean.BinderInfo.default))
Jakob von Raumer (Jun 01 2022 at 07:41):
Is there any way to reduce an Expr
in a way that minimizes the constructors used? I.e. reducing away not only let
s but also proj
s and literals?
Sebastian Ullrich (Jun 01 2022 at 07:47):
No built-in way I think, since Lean of course wants to preserve these
Mario Carneiro (Jun 01 2022 at 07:49):
Note that lean does know that a projection can unfold:
example : Foo.aa = @Foo.rec (λ _ => Nat) (λ x y => x) := rfl
Mario Carneiro (Jun 01 2022 at 07:49):
(on second thought, this might be eta for structures kicking in instead)
Jakob von Raumer (Jun 01 2022 at 07:54):
Sebastian Ullrich said:
No built-in way I think, since Lean of course wants to preserve these
For all kinds of transformations it is a bit weird to work on those doublets though, since making the transformation consistent already determines them uniquely
Sebastian Ullrich (Jun 01 2022 at 08:13):
Mario Carneiro said:
(on second thought, this might be eta for structures kicking in instead)
It's actually older than that, see isDefEqProj
. And isDefEqNat/isDefEqStringLit
for literals.
Last updated: Dec 20 2023 at 11:08 UTC