On Wednesday, 20 August 2014 at 20:18:15 UTC, Dicebot wrote:
On Wednesday, 20 August 2014 at 20:01:05 UTC, Colin wrote:
I see 3 distinct parts playing a role in my confusion:
A) The 'is' keyword. What does it do when you have is(expression);

http://dlang.org/expression.html#IsExpression

It is a tool for type checking. It has many options but plain `is(T)` checks if `T` is a valid type and returns `true` if it is. `void` is considered a valid type.

B) typeof( expression ); whats this doing? Particularly when the expression its acting on is a closure that returns nothing? (at least as far as I can see)

typeof(() {}) evaluates to void:

static assert(is(typeof(() {}) == void));

However, if any compilation errors happen inside the delegate, it evaluates to special invalid type which yield `false` when supplied to `is` expression.

Thus `is(typeof(expr))` is a way to express a concept "if `expr` compiles". Delegate is necessary to test statements because `typeof` only accepts expressions.

C) The closure expression:
(inout int = 0) {
  // Check to see if I can do InputRangy stuff...
}
Why is there a need for that inout int = 0 clause at the start of it?

Now this is a really weird one. This is necessary for input ranges with `inout` functions to fit the trait because `inout` variables can be declared only inside `inout` functions. See this bug report for details : https://issues.dlang.org/show_bug.cgi?id=7824

It is one of surprising feature inter-operation cases you don't expect when designing features :)

Thanks all, that explains it.

It is weird looking code alright, but I guess it has its uses.

I think I prefer the __traits(compiles,...) construct, as it is a bit more obvious as to what I'm checking. So will use that I suspect.

Cheers!

Reply via email to