On Fri, 20 Apr 2012 15:21:12 -0400, Robert Clipsham <[email protected]> wrote:

I've been staring blankly at this for a while now and want some input from others:

----
void foo(T, U...)(bool arg)
{
     if (arg)
     {
         assert(T.tupleof.length == U.length);
         assert(arg); /* Line 6 */
         // Or some other code here
     }
}
struct A {}
void main()
{
     foo!(A, int)(false);
}
----

When compiled with warnings:

$ dmd -w test.d
test.d(6): Warning: statement is not reachable

So what appears to be happening here is that dmd is constant folding T.tupleof.length == U.length to false, then assert(arg) can never happen, so the warning is given.

Also note that assert(0), which is what that line reduces to, is *not* removed for release builds.


It is obvious, however, that the assertion will never be executed anyway.

No it isn't. this:

foo!(A, int)(true);

compiles to the same exact template function instantiation. arg is a runtime parameter, not determinable at compile-time, and therefore the compiler must include the branch.

Is there some way around this? (other than compiling without -w)
I can't help but feel what I'm doing isn't right some how.

Use static assert/static if when you expect something that is determined at compile time to be a certain way. Not only will it be more efficient code, but if it's *not* compile-time determined, you will get an error from the compiler.

-Steve
  • Is this a bug? Robert Clipsham
    • Re: Is this a bug? Steven Schveighoffer

Reply via email to