...хорошо, непосредственно это синтаксис не поддерживает, поскольку массив
констант Array of Const подобен открытым массивам, главным образом в части
характеристик времени компиляции. Но вы можете обойти этот неприятный момент,
обладая хотя бы начальными знаниями того, как реализован открытый массив. Что
нам для этого необходимо: динамически размещенный массив array of TVarRec,
который "принимает" ваши параметры, и "псевдоним" (alias) функции Format,
позволяющий работать с таким массивом без "ругани" со стороны компилятора.
type{ объявляем тип для динамического массива array of TVarRecs }
TVarArray = array[0..High(Word) div Sizeof(TVarRec) - 1] of TVarRec;
PVarArray = ^TVarArray;
{ Объявляем alias-тип для функции Format. Передаваемые параметры будут иметь
в стеке тот же самый порядок вызова, что и при нормальном вызове Format }
FormatProxy = function(const aFormatStr: string; var aVarRec: TVarRec;
highIndex: Integer): string;
{ AddVarRecs копирует параметры, передаваемые в массиве A в pRecs^, начиная
с pRecs^[atIndex]. highIndex - самый большой доступный индекс pRecs, число
распределенных элементов - 1. }procedure AddVarRecs(pRecs: PVarArray; atIndex, highIndex: Integer; const A:
arrayofconst);
var
i: Integer;
beginif pRecs <> nilthenfor i := 0 to High(A) dobeginif atIndex <= highIndex thenbegin
pRecs^[atIndex] := A[i];
Inc(atIndex);
end{ If }else
Break;
end; { For }end; { AddVarRecs }procedure TScratchMain.SpeedButton2Click(Sender: TObject);
var
p: PVarArray;
S: string;
Proxy: FormatProxy;
begin{ распределяем массив для четырех параметров, индексы - 0..3 }
GetMem(p, 4 * Sizeof(TVarRec));
try{ добавляем параметры последующими вызовами AddVarRecs }
AddVarRecs(p, 0, 3, [12, 0.5, 'Шаблон']);
AddVarRecs(p, 3, 3, ['Тест']);
{ получаем полномочия Format }
@Proxy := @SysUtils.Format;
{ Вызов с динамически сгенерированным массивом параметров.
Естественно, строка формата может также быть сформирована
и во время выполнения программы. }
S := Proxy('Целое: %d, Реальное: %4.2f, Строки: %s, %s', p^[0], 3);
{ выводим результат }
ShowMessage(S);
finally
FreeMem(p, 4 * Sizeof(TVarRec));
end;
end;
Я надеюсь вы поняли принцип. Естественно, имеются ограничения. Вы можете
передавать в AddVarRecs числовые величины, строковые переменные и литералы, но
не в коем случае не строковые выражения! В этом случае компилятор должен для
хранения результата сформировать в стеке временную строку, передать ее в
AddVarRecs (или лучше по адресу в TVarRec), и она может прекратить свое
существование или может быть перезаписана в стеке другими данными, если в
конечном счете вы передадите в Proxy целый массив!
Тестировалось только в Delphi 1.0!
Массив констант во время выполнения приложения: описывается способ обхода ограничений синтаксиса языка Pascal, создавая динамически размещенный массив и используя функцию Format с помощью псевдонима.
Комментарии и вопросы
Получайте свежие новости и обновления по Object Pascal, Delphi и Lazarus прямо в свой смартфон. Подпишитесь на наш Telegram-канал delphi_kansoftware и будьте в курсе последних тенденций в разработке под Linux, Windows, Android и iOS