Examples of templated types.
1 static struct S(T) {} 2 static class C(T) {} 3 4 static assert( isInstantiationOf!(S, S!int)); 5 static assert( isInstantiationOf!(S, S!int)); 6 static assert( isInstantiationOf!(S, S!string)); 7 static assert( isInstantiationOf!(S, const S!string)); 8 static assert( isInstantiationOf!(S, shared S!string)); 9 static assert(!isInstantiationOf!(S, int)); 10 static assert(!isInstantiationOf!(S, C!int)); 11 static assert(!isInstantiationOf!(S, C!string)); 12 static assert(!isInstantiationOf!(S, C!(S!int))); 13 14 static assert( isInstantiationOf!(C, C!int)); 15 static assert( isInstantiationOf!(C, C!string)); 16 static assert( isInstantiationOf!(C, const C!string)); 17 static assert( isInstantiationOf!(C, shared C!string)); 18 static assert(!isInstantiationOf!(C, int)); 19 static assert(!isInstantiationOf!(C, S!int)); 20 static assert(!isInstantiationOf!(C, S!string)); 21 static assert(!isInstantiationOf!(C, S!(C!int))); 22 23 static struct Variadic(T...) {} 24 25 static assert( isInstantiationOf!(Variadic, Variadic!())); 26 static assert( isInstantiationOf!(Variadic, Variadic!int)); 27 static assert( isInstantiationOf!(Variadic, Variadic!(int, string))); 28 static assert( isInstantiationOf!(Variadic, Variadic!(int, string, int))); 29 static assert( isInstantiationOf!(Variadic, const Variadic!(int, short))); 30 static assert( isInstantiationOf!(Variadic, shared Variadic!(int, short))); 31 static assert(!isInstantiationOf!(Variadic, int)); 32 static assert(!isInstantiationOf!(Variadic, S!int)); 33 static assert(!isInstantiationOf!(Variadic, C!int)); 34 35 static struct ValueArg(int i) {} 36 static assert( isInstantiationOf!(ValueArg, ValueArg!42)); 37 static assert( isInstantiationOf!(ValueArg, ValueArg!256)); 38 static assert( isInstantiationOf!(ValueArg, const ValueArg!1024)); 39 static assert( isInstantiationOf!(ValueArg, shared ValueArg!1024)); 40 static assert(!isInstantiationOf!(ValueArg, int)); 41 static assert(!isInstantiationOf!(ValueArg, S!int)); 42 43 int i; 44 45 static struct AliasArg(alias Symbol) {} 46 static assert( isInstantiationOf!(AliasArg, AliasArg!42)); 47 static assert( isInstantiationOf!(AliasArg, AliasArg!int)); 48 static assert( isInstantiationOf!(AliasArg, AliasArg!i)); 49 static assert( isInstantiationOf!(AliasArg, const AliasArg!i)); 50 static assert( isInstantiationOf!(AliasArg, shared AliasArg!i)); 51 static assert(!isInstantiationOf!(AliasArg, int)); 52 static assert(!isInstantiationOf!(AliasArg, S!int)); 53 54 // An uninstantiated template is not an instance of any template, 55 // not even itself. 56 static assert(!isInstantiationOf!(S, S)); 57 static assert(!isInstantiationOf!(S, C)); 58 static assert(!isInstantiationOf!(C, C)); 59 static assert(!isInstantiationOf!(C, S)); 60 61 // Variables of a templated type are not considered instantiations of that 62 // type. For templated types, the overload which takes a type must be used. 63 S!int s; 64 C!string c; 65 static assert(!isInstantiationOf!(S, s)); 66 static assert(!isInstantiationOf!(C, c));
Examples of partial instantation.
static struct SingleArg(T) {} static struct Variadic(T...) {} alias isSingleArg = isInstantiationOf!SingleArg; alias isVariadic = isInstantiationOf!Variadic; static assert( isSingleArg!(SingleArg!int)); static assert( isSingleArg!(const SingleArg!int)); static assert(!isSingleArg!int); static assert(!isSingleArg!(Variadic!int)); static assert( isVariadic!(Variadic!())); static assert( isVariadic!(Variadic!int)); static assert( isVariadic!(shared Variadic!int)); static assert( isVariadic!(Variadic!(int, string))); static assert(!isVariadic!int); static assert(!isVariadic!(SingleArg!int)); T foo(T)(T t) { return t; } T likeFoo(T)(T t) { return t; } bool bar(alias pred)(int i) { return pred(i); } alias isFoo = isInstantiationOf!foo; alias isBar = isInstantiationOf!bar; static assert( isFoo!(foo!int)); static assert( isFoo!(foo!string)); static assert(!isFoo!int); static assert(!isFoo!(likeFoo!int)); static assert(!isFoo!(bar!(a => true))); static assert( isBar!(bar!(a => true))); static assert( isBar!(bar!(a => a > 2))); static assert(!isBar!int); static assert(!isBar!(foo!int)); static assert(!isBar!(likeFoo!int));
Evaluates to true if the given type or symbol is an instantiation of the given template.
The overload which takes T operates on types and indicates whether an aggregate type (i.e. struct, class, interface, or union) is an instantiation of the given template.
The overload which takes Symbol operates on function templates, because unlike with aggregate types, the type of a function does not retain the fact that it was instantiated from a template. So, for functions, it's necessary to pass the function itself as a symbol rather than pass the type of the function.
The overload which takes Symbol also works with templates which are not types or functions.
The single-argument overload makes it so that it can be partially instantiated with the first argument, which will often be necessary with template predicates.