John Launchbury wrote:
> Jeff,
>
> > Isn't that a bit of a dodgy argument? I don't know of any papers on `in'
> > polymorphism, but many about `let' polymorphism. If I see `let', I expect
> > polymorphism, and I'm not going to go searching for an `in'.
>
> Not true (or if true, misguided).
I say dodgy - you say misguided. OK - a fair enough trade ;-)
>
>
> > The ability to bind multiple things at once (and have the corresponding
> > increase in polymorphism) is a nice feature of a modern `let' - but it's not
> > the primary characteristic. The let in do could easily bind multiple things
> > as well (by allowing `in'). The currently syntax is just an aesthetic choice
> > isn't it?
>
> The current "let" in "do" already can bind multiple things. The reason for omitting
> the "in" is explicitly to avoid introducing another scope level (requiring a new
>"do",
> a new indent, etc.). How one expects it to behave depends on the implicit
> assumptions made about all the variables being bound in the "do". Currently,
> even though "do" gives the appearance of introducing many variables all at the same
> declaration level, it actually intoduces a nested sequence of variable bindings,
> each possibly shadowing bindings earlier in the sequence. In this current setting
> it makes sense for "let" in "do" to be thought of having an implicit "in", and so
> its bound variable is polymorphic in the remainder of the "do". In a recursive "do"
> (as in a "let"), all the newly bound variables are actually considered to be in
> a concurrent scope -- as suggested by the layout. In this setting, any variables
>bound
> by "let" are also part of the same scope as the others -- we have one big binding
> group -- hence they are monomorphic when used by other declarations in the same
> binding group.
Aha - the source of confusion. I hadn't made the leap that you were making do bindings
into one large binding group. This is a potentially more significant change than just
the polymoprhism-of-let issue.
So the problem is how to divvy up the binding group to get useful polymorphism. What
if,
for the purposes of doing the dependency analysis, you treated sequential do bindings
(the <- type, not let-in-do) as monolithic, then otherwise proceeded normally with the
strongly connected components analysis (taking care, if necessary, to keep do-binding
subgroups otherwise in order). For current uses of do and let, this should preserve
the
current polymorphic behaviour, since there won't be any backward dependecies and you
can
just nest the bindings (unless someone uses shadowing, but then they're in trouble
anyway
;-) . OK, I'll just go and read the paper, since I'm sure you've already thought about
this...
--Jeff