Paulo Sequeira
2013-06-18 22:23:16 UTC
Hi,
I've been looking at the coroutine idea from the http server4 and wanted
to try using it to make a simple generator. But I'm having trouble with
grasping the proper use of the "yield return expr" form and testing for
the completion of the coroutine.
For example, here's what I thought would be a simple generator that
would yield only one value and then complete:
struct int_gen : coroutine {
int operator()() {
reenter(this) {
yield return 1;
}
}
};
If I were using this generator, I would think that, after calling it
once, testing for is_complete() would return true and thus I would know
I shouldn't call into the generator again. But it seems is_complete() is
returning true one call-too-late. Like in what follows:
void main() {
int i = 3;
int_gen g;
i = g();
assert(i == 1);
i = 2;
assert(!g.is_complete());
i = g();
assert(g.is_complete());
//assert(i == ???);
}
Note that, after the first call to g(), g.is_complete() still returns
false; it is not until after the second call to g() that is_complete
returns true, but by that time, it already destroyed the contents of the
i variable.
What concerns me most is the fact that g() is running into undefined
behaviour because no return statement is actually being executed in the
second call, so there's something I'm not doing right at all. What would
be the appropriate way to code the generator with the help of the
coroutine class?
Best regards,
Paulo Sequeira
I've been looking at the coroutine idea from the http server4 and wanted
to try using it to make a simple generator. But I'm having trouble with
grasping the proper use of the "yield return expr" form and testing for
the completion of the coroutine.
For example, here's what I thought would be a simple generator that
would yield only one value and then complete:
struct int_gen : coroutine {
int operator()() {
reenter(this) {
yield return 1;
}
}
};
If I were using this generator, I would think that, after calling it
once, testing for is_complete() would return true and thus I would know
I shouldn't call into the generator again. But it seems is_complete() is
returning true one call-too-late. Like in what follows:
void main() {
int i = 3;
int_gen g;
i = g();
assert(i == 1);
i = 2;
assert(!g.is_complete());
i = g();
assert(g.is_complete());
//assert(i == ???);
}
Note that, after the first call to g(), g.is_complete() still returns
false; it is not until after the second call to g() that is_complete
returns true, but by that time, it already destroyed the contents of the
i variable.
What concerns me most is the fact that g() is running into undefined
behaviour because no return statement is actually being executed in the
second call, so there's something I'm not doing right at all. What would
be the appropriate way to code the generator with the help of the
coroutine class?
Best regards,
Paulo Sequeira