On Friday, 10 October 2014 at 21:26:49 UTC, Steven Schveighoffer wrote:
On 10/10/14 5:15 PM, IgorStepanov wrote:
On Friday, 10 October 2014 at 20:47:45 UTC, Steven Schveighoffer wrote:
On 10/10/14 1:09 PM, IgorStepanov wrote:
I've created DIP for my pull request.
DIP: http://wiki.dlang.org/DIP66
PR: https://github.com/D-Programming-Language/dmd/pull/3998

Please, comment it.

This part:

void test()
   {
       C c;
       int i = c; //Error: c.a.i vs c.b.i
   }

static assert(is(C : int)); //Ok, because C is subtype of int anyway.

I think might be wrong. There is a lot of code out there that says, e.g.:

void foo(T)(T t) if(is(T : U))
{
 U u = t;
 ...
}

Which will now create an error in the wrong place. IMO, the 'is' test
should also fail.

-Steve

I thought exactly about this using case.

See:
You have a struct like this in first place:
    struct A
    {
        int i;
        alias i this;
    }

    struct C
    {
        A a;
        string s;
        alias a this;
        alias s this;
    }

And you have a template function in second place:
void foo(T)(T t) if(is(T : int))
{
...
}

void foo(T)(T t) if(is(T : string))
{
...
}


And you have the code it third place:
C c;
foo(c); //Error: what do you mean: foo!(T : string) or foo!(T : int)

I agree with all this.

Now, someone (A developer) changed the A definition:

    struct A
    {
        int i;
        alias i this;
    }

    struct B
    {
        int i;
        alias i this;
    }

    struct C
    {
        A a;
        B b;
        string s;
        alias a this;
        alias b this;
        alias s this;
    }

And now, you code mystically start to works.

Why? It's just as confused as before, no?

The way the DIP reads, the call to foo(c) compiles, but the instantiation fails. This can cause subtle issues when you want to select an instantiation based on what it casts to.

An example:

foo(T)(T t) if(is(T : int))
{
   someFuncThatTakesInt(t);
}

foo(T)(T t) if(!is(T : int) && is(T.shadow : int))
{
   someFuncThatTakesInt(t.shadow);
}

struct A
{
   int i;
   alias i this;
}

struct B
{
   int i;
   alias i this;
}

struct C
{
   A a;
   B shadow;
   alias a this;
   alias shadow this;
}

C c;
foo(c); // should compile, but I think your DIP makes it fail due to ambiguity

-Steve

You can write foo(c.shadow); This isn't hard.
Ok, I understood you, let's listen to what others say

Reply via email to