On Wednesday, 12 June 2013 at 09:16:30 UTC, Timothee Cour wrote:
Why not use a castConstSafe function that'll transform A!T into A!(const
T), generically:

auto ref castSafe(T,S)(auto ref S a){...}
S a; T b=castSafe!T(a); //same as T b=cast(T)(a) except that it only compiles if S=>T only involves nonconst=>const conversions (works
recursively):
example: A!(double) => A!(const double) is allowed but not other direction.

More specifically:
auto ref castConstSafe(S)(auto ref S a){...} //transforms A!T into A!(const
T), generically

then:
void foo(B a) if (is(ElementType!B == const)){...}
A!(const double) a1;
A!(double) a2;
foo(a1.castConstSafe); //works
foo(a2.castConstSafe); //works

All it requires is to pass a.castConstSafe instead of a.

Because Foo!T and Foo!(const T) are completely unrelated types. Casting from one to the other gives 0 guarantees it actually works. For example:

//----
struct Foo(T)
{
    static if (is(T == const int))
    {
        void do_it()const{writeln("this");}
    }
    else
    {
        void do_it()const{writeln("that");}
    }
}

void main()
{
    Foo!int a;
    const(Foo!int)*  pa = &a;
    Foo!(const int)* pb = cast(Foo!(const int)*) &a;
    pa.do_it(); //prints "that"
    pb.do_it(); //prints "this"
}
//----

Of course, I could have also changed the members, making memory mapping incompatible, amongst others...

Reply via email to