This compiles, but it's an error because the array is mixed, &sqr is not pure: void main() { double sqr(double x) { return x * x; } pure double psqr(double x) { return x * x; } pure double delegate(double)[] funcs = [&sqr, &psqr]; } This doesn't compile, but pure functions are a subsets of impure functions: pure real sqr1(real x) { return x * x; } real sqr2(real x) { return x * x; } void main() { real function(real x)[] funcs = [&sqr1, &sqr2]; } While this compiles: void main() { double sqr(double x) { return x * x; } pure double psqr(double x) { return x * x; } double delegate(double)[] funcs = [&sqr, &psqr]; } The following doesn't compile, but nothrow functions are a subset of throwing functions: nothrow real sqr1(real x) { return x * x; } real sqr2(real x) { if (x == 0) throw new Error(""); return x * x; } void main() { real function(real x)[] funcs = [&sqr1, &sqr2]; } (Similar things happen with "pure nothrow" functions/delegates.)
With dmd 2.051beta all four examples don't compile, so the DMD is more strict.
This D2 program shows a cost of a strong type system: creating collections of functions becomes a problem because there are so many attributes that change a type. This specific problem is solved managing correctly variance/covariance of function pointers and delegates, typing the array 'a' as an array of impure nothrow @trusted functions: import std.math; void main() { auto a = [&asin, &cbrt]; }
I'm going to mark this as a dupe of 3180, along with 4000, as both cases are covered by covariance. *** This issue has been marked as a duplicate of issue 3180 ***