вторник, 3 декабря 2013 г.

Необязательный параметр в процедуре (Вариант 1. Открытые массивы)

Рассмотрим открытые массивы, которые позволяют передавать в функцию или процедуру различное количество параметров. В качестве параметров можно передать либо открытый массив элементов одинакового типа, либо массивы констант различного типа. В приведенном ниже примере объявляется функция, которой в качестве параметра должен передаваться открытый массив целых чисел. 


function AddEmUp( A: array of integer ): integer;


В открытом массиве можно передавать переменные, константы или выражения из констант. Ниже приведен пример, который демонстрирует вызов функции AddEmUp с передачей ей нескольких различных элементов. 


const
  j = 23;
var
  i, Rez: integer;
begin
   i := 8;
   Rez := AddEmUp( [i, 20, j, 43] );
end; 


Для получения информации о фактически передаваемом массиве параметров в функции или процедуре могут использоваться функции High, Low и SizeOf. Для иллюстрации их использования ниже приведен текст функции AddEmUp, которая возвращает сумму всех переданных ей элементов массива A. 


function AddEmUp( A: array of integer ): integer;
var
   i: integer;
begin
   Result := 0;
   for i := Low(A) to High(A) do
       Inc( Result, A[i] );
end; 


Object Pascal также поддерживает тип array of const, который позволяет передавать в одном массиве данные различных типов. Синтаксис объявления функций или процедур, использующих такой массив для получения параметров, следующий: 

procedure WhatHaveIGot( A: array of const ); 


Вызвать объявленную выше функцию можно, например, с помощью такого оператора:


procedure WhatHaveIGot( ['Text', 10, 5.5, @WhatHaveIGot, 3.14, true, 'c'] ); 


При передаче функции или процедуре массива констант все передаваемые параметры компилятор неявно конвертирует в тип TVarRec. Тип данных TVarRec объявлен в модуле System следующим образом: 


PVarRec = ^TVarRec;
TVarRec = record case
  Byte of vtInteger: (VInteger: Integer; VType: Byte);
        vtBoolean: (VBoolean: Boolean);
        vtChar: (VChar: Char);
        vtExtended: (VExtended: PExtended);
        vtString: (VString: PShortString);
        vtPointer: (VPointer: Pointer);
        vtPChar: (VPChar: PChar);
        vtObject: (VObject: TObject);
        vtClass: (VClass: TClass);
        vtWideChar: (VWideChar: WideChar);
        vtPWideChar: (VPWideChar: PWideChar);
        vtAnsiString: (VAnsiString: Pointer);
        vtCurrency: (VCurrency: PCurrency);
        vtVariant: (VVariant: PVariant);
        vtInterface: (VInterface: Pointer);
        vtWideString: (VWideString: Pointer);
        vtInt64: (VInt64: PInt64);
end;


Поле VType определяет тип содержащихся в данном экземпляре записи TVarRec данных и может принимать одно из ниже приведенных значений.

const
  vtInteger = 0;
  vtBoolean = 1;
  vtChar = 2;
  vtExtended = 3;
  vtString = 4;
  vtPointer = 5;
  vtPChar = 6;
  vtObject = 7;
  vtClass = 8;
  vtWideChar = 9;
  vtPWideChar = 10;
  vtAnsiString = 11;
  vtCurrency = 12;
  vtVariant = 13;
  vtInterface = 14;
  vtWideString = 15;
  vtInt64 = 16; 


Поскольку массив констант способен передавать данные разных типов, это может вызвать определенные затруднения при создании обрабатывающей полученные параметры функции или процедуры. В качестве примера работы с таким массивом рассмотрим реализацию процедуры WhatHaveIGot, которая просматривает элементы полученного массива параметров и выводит их тип. 


procedure WhatHaveIGot( A: array of const );
var
   i: integer; TypeStr: string;
begin
   for i := Low(A) to High(A) do begin
     case A[i].VType of
          vtInteger : TypeStr := 'Integer';
          vtBoolean : TypeStr := 'Boolean';
          vtChar : TypeStr := 'Char';
          vtExtended : TypeStr := 'Extended';
          vtString : TypeStr := 'String';
          vtPointer : TypeStr := 'Pointer';
          vtPChar : TypeStr := 'PChar';
          vtObject : TypeStr := 'Object';
          vtClass : TypeStr := 'Class';
          vtWideChar : TypeStr := 'WideChar';
          vtPWideChar : TypeStr := 'PWideChar';
          vtAnsiString : TypeStr := 'AnsiString';
          vtCurrency : TypeStr := 'Currency';
          vtVariant : TypeStr := 'Variant';
          vtInterface : TypeStr := 'Interface';
          vtWideString : TypeStr := 'WideString';
          vtInt64 : TypeStr := 'Int64';
    end;
   ShowMessage( Format( 'Array item %d is a %s', [i, TypeStr] ) );
  end;
end;

Найдено на http://programmersforum.ru/

Комментариев нет:

Отправить комментарий