closures
bearophile
bearophileHUGS at lycos.com
Thu Jul 16 11:33:58 PDT 2009
Jens:
> // On dmd v2.029, linux build, this...
> call(makedelegate1()); // ...works: 27
> call(makedelegate2()); // ...works: 7
> call(makedelegate3()); // ...doesn't work: 134518855
> call(makedelegate4()); // ...doesn't work: 134518947
> Foo f;
> call(&f.bar); // ...works: 7
I have run your code with DMD v2.031 on Windows, and it prints:
foo: 27
foo: 7
foo: 7
foo: 7
foo: 7
That sounds too much good, probably the right values are left in the stack. So I have added some printf() that return an int and show better the problems:
import std.stdio: writefln, printf;
struct Foo {
int a = 7;
int bar() { return a; }
int delegate() makeDelegate() {
printf("filler");
int abc() { return a; }
printf("filler");
return &abc;
}
}
void call(int delegate() dg) {
writefln("foo: %d", dg());
}
int delegate() makeDelegate1() {
int x = 27;
int abc() { return x; }
return &abc;
}
int delegate() makeDelegate2() {
Foo f;
int abc() { return f.a; }
return &abc;
}
int delegate() makeDelegate3() {
Foo f;
return &f.bar;
}
int delegate() makeDelegate4b(ref Foo f) {
int abc() { return f.a; }
printf("filler");
return &abc;
}
int delegate() makeDelegate4() {
Foo f;
printf("filler");
return makeDelegate4b(f);
}
void main() {
auto d1 = makeDelegate1();
printf("filler");
call(d1);
auto d2 = makeDelegate2();
printf("filler");
call(d2);
auto d3 = makeDelegate3();
printf("filler");
call(d3);
auto d4 = makeDelegate4();
printf("filler");
call(d4);
Foo f;
call(&f.bar);
}
Now the output is:
fillerfoo: 27
fillerfoo: 7
fillerfoo: 4354187
fillerfillerfillerfoo: 7
foo: 7
It shows some difference still compared to your output. So are some things improved between 2.029 and 2.031?
I don't know much about where and when to add "scope" to avoid creation of closures. Maybe Andrei's book will help me understand/learn better :-)
Bye,
bearophile
More information about the Digitalmars-d-learn
mailing list