Объявления типов для массивов и ассоциативных массивов, особенно для многомерных массивов удобно читать справа налево. Примеры будут ниже с комментариями.
У него размер известен на этапе компиляции, (содержимое может меняться, если явно не запрещено):
// RU: "a1 - массив с тремя элементами типа int"
int[3] a1;
У него и длина и содержимое меняется во время выполнения программы
// RU (справа-налево): "a2 - массив интов"
int[] a2;
При одинаковом (по сути) синтаксисе, динамические многомерные массивы реализованы, как массивы указателей не массивы, а статические как "плоские прямоугольные матрицы" по соображениям более высокой производительности:
// RU: b1 - матрица: массив с тремя элементами-массивами по четыре элемента типа int в каждом
int[4][3] b1;
int[][] b2; // динамический массив массивов
Указатели являются небезопасным средством языка.
int* p; // указатель p
p = a2.ptr; // теперь p указывает на первый элемент a2
int*[] p1; // p1 - динамический массив указателей
Операция среза создает ссылку на непрерывный диапазон ячеек исходного массива
int[] a1 = [3,4,5,6,7];
auto a2 = a1[1..3]; // [4,5,6]
auto a3 = a1[]; // ссылка на все содержимое a1
В операциях доступа к элементам a[$] - это синоним a[a.length]
a1[] *=2; // каждый элемент a1 увеличивается в два раза на месте
a1[1..3] +=1; // элементы с индексами 1 и 2 (3 - не входит) увеличиваются на единицу
Динамические массивы позволяют менять их длину путем установки нового значения length:
int[] a1 = [3,4,5];
a1.length = 5;
a1[3]=6;
a1[4]=7;
Для копирования элементов нужно в левой части присваивания использовать оператор среза []:
int[] a1 = [3,4,5];
int[] b1;
b1.length = a1.length;
b1[] = a1; // Копирование.
// b1 = a1 // ! если сделать так, то b1 будет ссылкой на a1
b1[0] = 10; // не затронет a1, если b1 - копия
writefln("%s %s", a1,b1); // [3, 4, 5] [10, 4, 5]
Оператор ~ создает новый массив как объединение копий исходных
auto a1 = [3,4,5];
auto b1 = [6,7,8];
auto c1 = a1 ~ b1;
c1[0]=10;
writefln("%s %s %s", a1, b1, c1); // [3, 4, 5] [6, 7, 8] [10, 4, 5, 6, 7, 8]
a ~= b; // массив a стал объединением a и b
auto a1 = [3,4,5];
int[] b1;
b1.length = a1.length; // целевой массив той же длины
b1[] = a1[]+1;
writefln("%s %s", a1, b1); // [3, 4, 5] [4, 5, 6]
.init // для статического массива: инициализирует все элементы дефолтным значением
.length // количество элементов
.sizeof // длина в байтах
.ptr // указатель на первый элемент
.dup // изменяемая копия
.idup // неизменяемая копия
.sort, .reverse // сортировка, обратный порядок на месте
.reserve(N); // резервирование памяти как минимум для N элементов
.capacity // сколько может вместить массив без реаллокации (дорогостоящая операция)
myarray.foo(3); // вызов функции, идентично: foo(myarray, 3);
Строки - это неизменяемые массивы типа char:
string s1 = "abx";
immutable (char)[] s2 = "abx";
assert( s1==s2);
writefln("%s %s", s1, s2); // abx abx