alias
создает новое имя для существующего. typedef
работает только с типами и фактически создает новый тип:
alias int A;
typedef int B;
pragma(msg, is(A == int)); // true
pragma(msg, is(B == int)); // false
С помощью typedef
вы также можете изменить инициализатор по умолчанию:
typedef int A = 42;
A a;
A[5] b;
void main()
{
assert(a == 42);
foreach(i; b) assert(i == 42);
}
alias
является более общим. Также работает с символами:
import std.stdio;
import std.conv : to;
alias to!(string) toString;
void main()
{
int a;
alias a b;
a = 1;
writeln(b); // 1
string s = toString(2);
writeln(s); // 2
}
alias
также используется, когда вы хотите объединить наборы перегрузки:
import std.stdio;
class Base
{
void foo() { writeln("base"); }
}
class Derived : Base
{
alias super.foo foo; // merge overload sets
void foo(int i) { writeln("derived"); }
}
void main()
{
auto a = new Derived;
a.foo(); // base
a.foo(0); // derived
}
Без явного слияния вызов Base.foo
с использованием экземпляра Derived
недопустим, поскольку Derived.foo
скрывает его по умолчанию.
Это требуется не только для занятий; если функции из двух разных импортированных модулей перегружают друг друга, они должны быть явно объединены с alias
.
typedef
устарело. Начиная с версии DMD 2.057, использование typedef
требует для компиляции флага -d
(для устаревших).
Этот запрос извлечения добавляет шаблон TypeDef
к std.typecons
, повторяющий функциональность typedef
в стандартной библиотеке.