Is there a standard way to define to for user-defined types?

kenji hara k.hara.pg at gmail.com
Mon Jun 20 05:14:15 PDT 2011


I have tried to conversion test.
----
import std.conv;

void main()
{
    tests1();
    tests2();
    testc1();
    testc2();
}

struct SS1{ ST1 opCast(T:ST1)(){ return ST1(); } }
struct ST1{  }
void tests1()
{
    SS1 s1;
    auto t1a = cast(ST1)(s1);       // -> s1.opCast!ST1()
//  auto t1b = to!ST1(s1);          // NG
}

struct SS2{  }
struct ST2{ this(SS2 source){} }
void tests2()
{
    SS2 s2;
    auto t2a = cast(ST2)(s2);       // -> ST2(s2) == ctor call
//  auto t2b = to!ST2(s2);          // NG
}

class CS1{ CT1 opCast(T:CT1)(){ return new CT1(); } }
class CT1{  }
void testc1()
{
    CS1 s1 = new CS1();
    auto t1a = cast(CT1)(s1);       // -> s1.opCast!CT1()
    auto t1b = to!CT1(s1);
        // T toImpl(T, S)(S value) if (is(S : Object) && is(T : Object))
        // -> cast(CT1)(s1)
        // -> s1.opCast!CT1()
}

class CS2{  }
class CT2{ static CT2 opCall(CS2 source){ return new CT2(); } }
//class CT2{ this(CS2 source){} }   // Unfortunately, ctor is not
called by CastExp.
void testc2()
{
    CS2 s2 = new CS2();
    auto t2a = cast(CT2)(s2);       // -> CT2(s2) == CT2.opCall(s2)
//  auto t2b = to!CT2(s2);          // compiled, but runtime error occurs
        // T toImpl(T, S)(S value) if (is(S : Object) && is(T : Object))
        // -> cast(CT1)(s1)
        // -> null
}
----

Some of thoughts of me:
1. std.conv.to should support built-in casting behavior, at least on
struct object.
   This feature was recently fixed. See bug5897.
2. Using to!T() member function by std.conv.to is unnecessary feature,
because it can be replaced by opCast!T.
3. For class object, I guess that is need to support 'Conversion
Interface that Intrude into TargetType'.
   I think 'conversion constructor call' is good fit to it.

Kenji


More information about the Digitalmars-d mailing list