The bizarre world of typeof()
Lars T. Kyllingstad
public at kyllingen.NOSPAMnet
Mon Oct 26 07:11:35 PDT 2009
Don wrote:
> Lars T. Kyllingstad wrote:
>> Don wrote:
>>> I'm trying to make sense of the rules for 'typeof'. It's difficult
>>> because DMD's behaviour is so different to the spec. Here's four
>>> simple cases.
>>>
>>> // This doesn't compile on D1.
>>> //alias typeof(int*int) Alias1;
>>>
>>> // This compiles in D1, but not in D2.
>>> alias int Int;
>>> alias typeof(Int*Int) Alias2;
>>>
>>> // Yet this DOES compile on D2 !
>>> typeof(T*U) foo(T, U)(T x, U y) { return x*y; }
>>> alias typeof(foo(Int, Int)) Alias3;
>>>
>>> // And this fails on both D1 and D2, with a dreadful error message.
>>> //alias typeof(foo(int)) Alias4;
>>>
>>> I can't see anything in the spec to say why ANY of these examples
>>> should compile. Yet, the existing template constraints features
>>> relies on the Alias3 case.
>>
>>
>> Here are a few more:
>>
>> class Foo { real bar() { return 1.0; } }
>> Foo foo = new Foo;
>>
>> // Passes, but should fail.
>> static assert (is (typeof(foo.bar) == function));
>>
>> // Passes, as expected.
>> static assert (is (typeof(&foo.bar) == delegate));
>>
>> // Passes, but should fail. This is similar to Don's examples.
>> static assert (is (typeof(Foo.bar) == function));
>>
>> // This one fails with the following hilarious message:
>> // Error: static assert (is(real function() == function)) is false
>> static assert (is (typeof(&Foo.bar) == function));
>>
>> I have no idea why typeof(&Foo.bar) even works, but it does. &Foo is
>> completely meaningless.
>
> Dot has higher precedence than &, so it means &(Foo.bar), not (&Foo).bar.
>
> The static assert fails because "real function()" is a *function
> pointer*, but is(xxx == function) tests to see if xxx is a *function*,
> not a *function pointer*.
>
> So this passes:
> void function () goo;
> static assert( is (typeof(*goo) == function));
>
> It's pretty awful that that in "is(real function() == function)", the
> keyword 'function' has two contradictory meanings in the same
> expression. And the spec never says what "function type" is.
Ok, I see now. It's not wrong then, just ugly. :)
static assert (is (int delegate() == delegate)); // passes
static assert (is (int function() == function)); // fails
What about my first example then, is that the intended behaviour as
well? With the current property syntax, I'd expect this to work, but it
doesn't:
static assert (is (typeof(foo.bar) == typeof(foo.bar())));
Error: static assert (is(real() == real)) is false
-Lars
More information about the Digitalmars-d
mailing list