Template iz
Iz
is a helper template that allows you to inspect a type or an alias.
template iz(Aliases...)
;
It takes a single element as an argument. The reason the template parameters is types as a variable arg sequence is becure if D does not allow (pre version 2.087) to say "I want either a type or alias over here, I don't care, I'll figure it out". But it does allow it when you use a template sequence parameter
method | Description |
---|---|
of |
True if the resolved type is the same as another resolved type |
sameAs |
True if T and U are the same "thing" (type, alias, literal value) |
nullType |
True if the resolved type is typeof(null) |
unaryOver |
True if the resolved type a unary funtion over some other types |
binaryOver |
True if the resolved type a binary funtion over some other types |
functionOver |
True if the resolved type an n-ary funtion over n types |
refType |
True if the resolved type a reference type |
valueType |
True if the resolved type a value type |
literalOf |
True if the resolved type is a literal of a type of T |
literal |
True if the resolved type is a literal |
copyConstructable |
True if resolved type is copy constructable |
nonTriviallyCopyConstructable |
True if resolved type is non-trivially copy constructable |
triviallyCopyConstructable |
True if resolved is trivially copy constructable |
equatableTo |
True if resolved type is equatabel to other |
nullTestable |
True if resolved type can be checked against null |
nullSettable |
True if resolved type can be set to null |
refDecl |
True if resolved type is declred with ref or is a function that returns ref |
See also
- https://dlang.org/spec/template.html#variadic-templates
Example
int i = 3;
int j = 4;
int *pi = null;
// Is it resolved to the same type as another?
static assert( iz!i .of!int);
static assert(!iz!i .of!(int*));
static assert( iz!3 .of!i);
static assert(!iz!int .of!pi);
// Is it the same as another?
static assert( iz!i .sameAs!i);
static assert(!iz!i .sameAs!j);
static assert( iz!1 .sameAs!1);
static assert(!iz!1 .sameAs!2);
// Using std.meta algorithm with iz
import std .meta: allSatisfy, AliasSeq;
static assert(allSatisfy!(iz!int .of, 3, 4, int, i));
/// Is it a function over
static assert( iz!(a => a) .unaryOver!int);
static assert( iz!((a, b) => a) .binaryOver!(int, int));
static assert( iz!((a, b, c, d) => a) .functionOver!(int, int, int, int));
// Is this thing a value or reference type?
struct SValueType {}
class CRefType {}
static assert( iz!SValueType .valueType);
static assert(!iz!CRefType .valueType);
static assert(!iz!SValueType .refType);
static assert( iz!CRefType .refType);
static assert( iz!"hello" .literalOf!string);
static assert(!iz!3 .literalOf!string);
// Is this thing copy constructable?
static struct SDisabledCopyConstructor { @disable this(ref typeof(this)); }
static assert(!iz!SDisabledCopyConstructor .copyConstructable);
static assert( iz!int .copyConstructable);
// Does this thing define a custom copy constructor (i.e. non-trivial copy constructor)
static struct SCopyConstructor { this(ref typeof(this)) {} }
static assert( iz!SCopyConstructor .nonTriviallyCopyConstructable);
static assert(!iz!SCopyConstructor .triviallyCopyConstructable);
static assert(!iz!int .nonTriviallyCopyConstructable);
static assert( iz!int .triviallyCopyConstructable);
// Can we equate these things?
static assert( iz!int .equatableTo!3);
static assert(!iz!3 .equatableTo!string);
// What null-semantics does the type have
// Is it settable to null?
static struct SNullSettable { void opAssign(int*) {} }
static assert( iz!pi .nullSettable);
static assert( iz!SNullSettable .nullSettable);
static assert(!iz!i .nullSettable);
// Is it checable with null? (i.e. if (this is null) )
static assert( iz!pi .nullTestable);
static assert(!iz!SNullSettable .nullTestable);
static assert(!iz!i .nullTestable);
// Is it typeof(null)?
static assert(!iz!int .nullType);
static assert( iz!null .nullType);
static assert( iz!(typeof(null)) .nullType);