www.digitalmars.com         C & C++   DMDScript  

digitalmars.D.learn - Template matching and is expression

reply Piotr Szturmaj <bncrbme jadamspam.pl> writes:
Hello,

I'm using D2.051 and following code:

import std.variant;

template Nullable(T)
{
     alias Algebraic!(T, void*) Nullable;
}

template isNullable(T)
{
     static if (is(T X == Nullable!U, U))
         enum isNullable = true;
     else
         enum isNullable = false;
}

static assert(isNullable!(Nullable!int));

and above static assert fails. Neither this works:

template isNullable(T : Nullable!U, U)
{
     enum isNullable = true;
}

template isNullable(T)
{
     enum isNullable = false;
}

static assert(isNullable!(Nullable!int));

Question is, what I'm doing wrong?
Dec 30 2010
parent reply "Simen kjaeraas" <simen.kjaras gmail.com> writes:
Piotr Szturmaj <bncrbme jadamspam.pl> wrote:

 static assert(isNullable!(Nullable!int));

 Question is, what I'm doing wrong?

The problem here is that Nullable!T is not a real type. Hence, Nullable!int is actually Algebraic!(int,void*). Checking for that apparently does not work as simply as one might hope. So, instead you should create a wrapper. This works: struct Nullable(T) { Algebraic!(T, void*) Nullable; alias Nullable this; } template isNullable(T) { static if (is(T X == Nullable!(U), U)) enum isNullable = true; else enum isNullable = false; } static assert(isNullable!(Nullable!int)); -- Simen
Dec 30 2010
parent Piotr Szturmaj <bncrbme jadamspam.pl> writes:
Simen kjaeraas wrote:
 Piotr Szturmaj <bncrbme jadamspam.pl> wrote:

 static assert(isNullable!(Nullable!int));

 Question is, what I'm doing wrong?

The problem here is that Nullable!T is not a real type. Hence, Nullable!int is actually Algebraic!(int,void*). Checking for that apparently does not work as simply as one might hope.

Algebraic is also an alias for VariantN (which is real type): template Algebraic(T...) { alias VariantN!(maxSize!(T), T) Algebraic; } however this check also yields false: static if (is(T X == VariantN!(U), U...)) but this works: static if (is(T == Nullable!int)) so, I was a bit confused... So, instead you should create a wrapper. This works:
 struct Nullable(T) {
 Algebraic!(T, void*) Nullable;
 alias Nullable this;
 }

 template isNullable(T) {
 static if (is(T X == Nullable!(U), U))
 enum isNullable = true;
 else
 enum isNullable = false;
 }

 static assert(isNullable!(Nullable!int));

Thanks! I've already used wrappers like that, but I though it's possible to match aliases directly. regards, Piotr
Dec 30 2010