MiniD 2 - Tentative Release Candidate 1

Jarrett Billingsley jarrett.billingsley at gmail.com
Wed Dec 10 20:45:19 PST 2008


On Wed, Dec 10, 2008 at 10:21 PM, davidl <davidl at 126.com> wrote:
> That's not true. All about compiler is easeing developers. Why not issue a compiler
> error/warning when it reaches some code like:
>
> function opApply(m) = coroutine function opApply(m)
>
> 1. the local var m shadows the arg m _in 1 declaration_
> 2. this could be a general mistake which could possibly be made by people with
>   a strong type programming background
>
> Probing this kind of code seems troublesome, I will be glad to see MiniD can give an error
> on this kind of code someday.

I'm not sure that's a good idea.  The compiler does already issue an
error if you declare a local multiple times in the same function:

local x

{
    local x // error, shadows previous declaration
}

But if that is generalized to disallowing local variable declarations
that shadow locals in any enclosing functions as well, .. ech.  It
seems a bit much.  I might implement it, I might not.

> That's pretty tricky. But the syntax of following is cleaner if possible:
> class count
> {
>        x = 3
>
>        coroutine function opApply() //mark it as a coroutine function.
>        {
>            yield()
>
>            for(i: 1 .. :x + 1)
>                yield(i)
>        }
> }
>
> global c = count()
>
> foreach(v; c)
>        writeln(v) // prints 1 through 4
>
> It's pretty sad "coroutine function" in a whole doesn't work.

I think you're confused about what "coroutine" is, grammatically.
"coroutine" is an expression.  Much like "-" in front of "5" gives the
number "-5", "coroutine" in front of an expression that evaluates to a
function gives a thread object.

Allowing something like "coroutine function" as a declaration is
inflexible.  Most of the time, the parameters to the coroutine are not
going to be the same as the parameters to the function which creates
it.  It seems like syntactic noise for little benefit.

> But still opApply() = coroutine function() still not work
>
> You do it: function f()=coroutine function()

..you don't have a body on that function.  Of course it's not going to work.

> I think if MiniD is able to do the syntax I proposed, I wouldn't have those bunch
> questions about foreach on a coroutine function.
> And People won't expect do foreach on a coroutine in most cases if that syntax comes
> true. Because for most people, a coroutine opApply is more intuitive than a coroutine
> with an opApply method available.

I've considered making coroutines a basic iterable type, in which case
their opApply would disappear.  (it would also make the "dummy" first
index disappear.)

> And I think it's practicle for MiniD compiler decide what to do, because MiniD can
> probe that if the opApply method is coroutine or not. If it's coroutine function, than
> implicitly a coroutine context created. Also the first yield is quite weird for me.

The first yield is there so that any extra parameters to the coroutine
object are passed before iteration starts, as well as to associate the
context ('this') parameter with it.

>
> class count
> {
>        x = 3
>
>        function opApply() = coroutine function() //mark it as a coroutine function.

Again I think you're getting a bit confused as to what "coroutine" is
doing.  opApply is not a "coroutine function".  opApply is a function
which returns a thread object.  That is,

function opApply() = coroutine function() {}

is equivalent to:

function opApply()
{
    local function blah() {}
    return coroutine blah
}

>        {
>            yield()     // I hope that we could get rid of the first yield, is that for something special or else?
>            for(i: 1 .. :x + 1)
>                yield(i)
>        }
> }
>
> global c = count()
>
> foreach(v; c)
>        writeln(v) // current it prints nothing. I don't know what it's actually going here.
>

I'll agree that that's a bit surprising.  What actually happens is
that on the first iteration, it notices that 'c' is not a function, so
it calls c.opApply().  It then happily assumes that opApply returned a
function, and calls it.  That is, it doesn't notice opApply returned a
coroutine, and so doesn't call opApply on the coroutine itself.  It
calls the coroutine, thinking it's a function, and the coroutine
yields nothing, which the foreach loop interprets as "end of
iteration."  Agh.

I'm liking the idea of making 'thread' a basic iterable type more and more ;)


More information about the Digitalmars-d-announce mailing list