Ни для кого не секрет, что Delphi XE7 получил улучшения в языке Object Pascal для работы с массивами. В этой статье мы разберёмся, что же появилось нового и пробежимся по уже имеющимся возможностям по работе с массивами.
Объявление и инициализация массива
Начнём, конечно, с объявления массива. Раньше в Delphi одной строкой можно было объявлять и инициализировать только статический массив. С динамическими массивами всё было гораздо сложнее: нужно было объявить массив, а затем инициализировать каждый его элемент. Теперь в Delphi XE7 динамический массив можно инициализировать прямо при объявлении. Или инициализировать позже, но тоже одной строкой. Вот пример программы с инициализацией статических и динамических массивов и их последующим чтением:
program Project1;
{$APPTYPE CONSOLE}
{$R *.res}
uses
System.SysUtils;
type
TIntArray = array of integer;
var
elem: integer;
dynElem1: TIntArray;
dynElem2: TArray<integer>;
i, j: integer;
//Статический массив.
statArray1: array[0..3] of integer = (0, 1, 2, 3);
//Статический двумерный массив.
statArray2: array[0..1] of array[0..2] of integer = ((0, 1, 2), (10, 11, 12));
//Динамический одномерный массив.
dynArray1: array of integer = [0, 1, 2, 3];
//Динамический одномерный массив (инициализация будет ниже).
dynArray2: array of integer;
//Динамический двумерный массив.
dynArray3: array of TIntArray = [[0, 1, 2, 3], [10, 11, 12]];
//Динамический двумерный массив.
dynArray4: array of array of integer = [[0, 1, 2, 3], [10, 11, 12]];
//Динамический одномерный массив.
dynArray5: TArray<integer> = [0, 1, 2, 3];
//Динамический двумерный массив.
dynArray6: TArray<TArray<integer>> = [[0, 1, 2, 3], [10, 11, 12]];
begin
try
WriteLn('Одномерный статический массив statArray1:');
for elem in statArray1 do
WriteLn(elem);
WriteLn('Двумерный статический массив statArray2:');
for elem in statArray2 do
Writeln(elem);
WriteLn('Одномерный динамический массив dynArray1:');
for elem in dynArray1 do
Writeln(elem);
WriteLn('Одномерный динамический массив dynArray2:');
dynArray2 := [7, 8, 9]; //Инициализация динамического массива.
for elem in dynArray2 do
Writeln(elem);
dynArray2 := []; //Удаляем все элементы массива.
WriteLn('Массив dynArray2 после очистки:');
for elem in dynArray2 do
Writeln(elem);
WriteLn('Двумерный динамический массив dynArray3:');
for dynElem1 in dynArray3 do
for elem in dynElem1 do
Writeln(elem);
WriteLn('Двумерный динамический массив dynArray4:');
for i := 0 to Length(dynArray4) - 1 do
for j := 0 to Length(dynArray4[i]) - 1 do
Writeln(dynArray4[i][j]);
WriteLn('Одномерный динамический массив dynArray5:');
for elem in dynArray5 do
Writeln(elem);
WriteLn('Двумерный динамический массив dynArray6:');
for dynElem2 in dynArray6 do
for elem in dynElem2 do
Writeln(elem);
ReadLn;
except
on E: Exception do
Writeln(E.ClassName, ': ', E.Message);
end;
end.
Как видно из кода, при объявлении многомерного массива при помощи конструкций «array of T», позже возникают проблемы с чтением массива в цикле «for in do». Приходится либо ходить по массиву с помощью цикла «for to do» (см. массив dynArray3) либо объявлять тип дочернего массива (см. массив dynArray2). Гораздо удобнее объявлять тип массива с помощью шаблона «TArray<T>». При объявлении многомерного массива таким способом при чтении можно использовать циклы «for in do» и «for to do».
Что касается смешанных массивов, то такие массивы удалось инициализировать в одну строку только в случае, когда динамический массив находится внутри статического, но не наоборот:
var
//Статический массив внутри динамического.
//Инициализировать такой массив в одну строку не удаётся.
multiArray1: array of array[0..1] of integer;
//Динамический массив внутри статического.
multiArray2: array[0..1] of array of integer = ([1, 2, 3], [10, 20, 30, 40]);
Конкатенация массивов, вставка и удаление элементов
Теперь с массивами можно работать так же, как и со строками, при условии, что массивы динамические и одного типа. Доступны функции Concat, Insert и Delete, а также оператор +.
Вот пример использования функции Concat:
var
dynArray1: TArray<integer> = [0, 1, 2, 3];
dynArray2: TArray<integer> = [4, 5, 6];
dynArray3: array of integer = [0, 1, 2];
begin
//Сложение двух массивов одного типа.
dynArray1 := Concat(dynArray1, dynArray2); //Результат будет [0, 1, 2, 3, 4, 5, 6]
//Добавление к массиву двух элементов.
dynArray3 := Concat(dynArray3, [3, 4]); //Результат будет [0, 1, 2, 3, 4].
end;
Тоже самое можно записать с помощью оператора +:
var
dynArray1: TArray<integer> = [0, 1, 2, 3];
dynArray2: TArray<integer> = [4, 5, 6];
dynArray3: array of integer = [0, 1, 2];
begin
//Сложение двух массивов одного типа.
dynArray1 := dynArray1 + dynArray2; //Результат будет [0, 1, 2, 3, 4, 5, 6]
//Добавление к массиву двух элементов.
dynArray3 := dynArray3 + [3, 4]; //Результат будет [0, 1, 2, 3, 4].
end;
А вот примеры использования функций Insert и Delete:
var
dynArray1: TArray<integer> = [0, 1, 2, 3];
dynArray2: TArray<integer> = [4, 5, 6];
dynArray3: array of integer = [0, 1, 2];
dynArray4: array of integer = [0, 1, 2, 4, 5];
begin
//Вставляем элементы массива dynArray2 внутрь массива dynArray1.
Insert(dynArray2, dynArray1, 2); //Результат будет [0, 1, 4, 5, 6, 2, 3]
//Вставляем в массив dynArray3 два элемента.
Insert([100, 200], dynArray3, 1); //Результат будет [0, 100, 200, 1, 2]
//Вставляем один элемент в массив dynArray4.
Insert(700, dynArray4, 3); //Результат будет [0, 1, 2, 700, 4, 5]
//Удаляем два элемента из массива.
Delete(dynArray4, 1, 2); //Результат будет [0, 700, 4, 5];
end;
Копирование массивов, изменение размера и другие возможности
Остальные замечательные функции для работы с массивами остались без изменений. Это Copy, Length, SetLength, Slice и функции для работы с многомерными массивами, такие как DynArrayBounds и DynArrayClear. Вот ещё несколько примеров по работе с массивами:
var
bound: TBoundArray;
dynArray1: TArray<integer> = [0, 1, 2, 3];
dynArray2: TArray<integer>;
dynArray3: TArray<TArray<integer>>;
begin
//Копирование 2-х элементов массива.
dynArray2 := Copy(dynArray1, 1, 2); //Результат будет [1, 2]
//Копирование массива начиная с элемента с индексом 1 и до конца.
dynArray2 := Copy(dynArray1, 1); //Результат будет [1, 2, 3]
//Копирование массива целиком.
dynArray2 := Copy(dynArray1); //Результат будет [0, 1, 2, 3]
//Устанавливаем размер двумерного массива.
SetLength(dynArray3, 10, 5);
//Получение размерности двумерного массива.
//Результат будет [9, 4] - максимальное значение для каждой размерности массива.
bound := DynArrayBounds(Pointer(dynArray3), TypeInfo(TArray<TArray<integer>>));
end;
Результат нововведений в Object Pascal
О новых возможностях по работе с массивами в Delphi можно сказать следующее. Разработчики сделали отличное улучшение, работать с массивами теперь станет намного удобнее. Остаётся только пожелать, чтобы язык продолжил развиваться в лучшую сторону. Будем ждать очередных фишек.
Комментарии
как создать и инициализировать массив битовых изображений *.bmp, *.jpg, затем вывести в TImage c помощью событий TTimer, В любом гиф-редакторе это делается на раз и два. В Делфи проблема!
Для gif в Дельфи есть класс TGIFImage, но если прямо нужно засовывать картинки в массив, то можно использовать коллекцию TObjectList, в которой будут храниться ссылки на объекты TImage.
RSS лента комментариев этой записи