alias, alias this, opDispatch and Advanced Type Tricks
30.1 alias
alias Integer = int; // type alias
alias StrMap = string[string];
alias print = writeln; // symbol alias
alias Callback = void delegate(int);
alias Vec = Vector!(float, 3);30.2 alias this (Subtyping and Implicit Conversion)
struct Meters
{
double value;
alias value this; // Meters implicitly converts to double
}
Meters m = Meters(5);
double d = m + 2.5; // works via alias this
struct LoggedArray(T)
{
T[] data;
alias data this; // forward everything to the array
void opOpAssign(string op : "~")(T x) { writeln("append ", x); data ~= x; }
}30.3 opDispatch (Dynamic-Like Members)
struct Dynamic
{
string[string] fields;
auto opDispatch(string name)() { return fields[name]; } // d.anything
void opDispatch(string name)(string v) { fields[name] = v; } // d.anything = v
}
Dynamic d;
d.color = "red";
writeln(d.color);
struct Swizzle
{
float x, y, z;
auto opDispatch(string s)() if (s.length > 1) // v.xy, v.zyx
{
float[s.length] r;
static foreach (i, c; s) r[i] = mixin("this." ~ c);
return r;
}
}30.4 Typedefs and Strong Types
import std.typecons : Typedef, Flag, Yes, No;
alias UserId = Typedef!(int, 0, "UserId"); // distinct type
void open(string path, Flag!"readOnly" ro = No.readOnly) {}
open("x", Yes.readOnly); // self-documenting boolean flags30.5 std.typecons Utilities
Tuple/tuple, Nullable, RefCounted/SafeRefCounted, Unique, scoped, Rebindable, BlackHole/WhiteHole/AutoImplement, wrap/unwrap (structural interface casting), Proxy, Ternary, Typedef, Flag, BitFlags, apply (for Nullable).