Советы по Delphi. Версия 1.4.3 от 1.1.2001 - страница 14
Delphi 1
>list:=Tlist.create;
>For i:= 1 to 1000 do begin
> SSObject:=TSSObject.create;
> {поместите куда-нибудь ссылку на созданный объект - например, в Tlist}
> list.add(SSObject);
>end;
Параметры
Передача функции как параметра
Delphi 1
В нашем случае лучшим решением будет использование процедурного типа. Допустим, что DllFunction() на входе хочет получить определенную функцию, поясним это на примере кода:
>type TMyFuncType = function: integer;
>var MyFunc : TMyFuncType;
>function foo: integer;
>begin
> result := 1;
>end;
>begin
> MyFunc := foo;
> DllFunction(longint(MyFunc));
Вы можете это сделать и так:
>DllFunction(longint(@foo));
Все же я не уверен в вопросах корректности использования таким образом в вызовах DLL памяти (для меня пока неясна работа с памятью, находящейся в другом сегменте), как в этом примере, так что возможно для корректной работы вам придется объявить foo с директивой far, экспортировать ее в модуле, или что-то еще.
Также, в зависимости от того, как написана DllFunction(), вы можете в вызове подразумевать приведение типа:
>function DllFunction(p: TMyFuncType): Integer; far; external 'mydll';
В этом случае вам не нужна будет переменная MyFunc или оператор @.
В Delphi/Pascal вы можете передавать функции как параметры. Тем не менее, чтобы этим воспользоваться, необходимо для компилятора установить тип. Попробуйте следующий код (я реально его компилил и тестировал):
>unit Unit1;
>interface
>uses
> SysUtils, WinTypes, WinProcs, Messages, Classes, Graphics, Controls,Forms, Dialogs, StdCtrls;
>type
> TForm1 = class(TForm)
> Button1: TButton;
> Button2: TButton;
> procedure Button1Click(Sender: TObject);
> procedure Button2Click(Sender: TObject);
> private { Private declarations }
> public { Public declarations }
> end;
>var
> Form1: TForm1;
>implementation
>{$R *.DFM}
>type
> IntFunc = function: integer;
>function DllFunction(iFunc: IntFunc): integer; far;
>begin
> DllFunction := iFunc; {Обратите внимание на то, что это вызов функции}
>end;
>function iFoo: integer; far;
>begin
> iFoo := 1;
>end;
>procedure TestIFunc;
>var
> i: integer;
>begin
> i := DllFunction(iFoo);
>end;
>procedure TForm1.Button1Click(Sender: TObject);
>begin
> TestIFunc;
>end;
>procedure TForm1.Button2Click(Sender: TObject);
>begin
> Close;
>end;
>end.
Вы можете сделать две вещи. Во-первых, если вы хотите использовать для передачи longint, напишите следующий код:
>i := longint(@foo)
Другая вещь, которую вы можете сделать — исключить работу с longint и вызывать функцию dll следующим образом:
>DLLfunction(@foo);
Имейте в виду, что если вы собираетесь вызывать foo из DLL, то необходимо предусмотреть вопросы совместимости, для получения дополнительной информации почитайте описание функции MakeProcInstance.
Проблема передачи записи
Delphi 1
Может это не то, что вы ищете, но идея такая:
Определите базовый класс с именем, скажем, allrecs:
>tAllrecs = class
> function getVal(field: integer): string; virtual;
>end;
Затем создаем классы для каждой записи:
>recA = class(tAllrecs)
> this: Integer;
> that: String;
> the_other: Integer;
> function getVal(field: integer): string; virtual;
>end;
Затем для каждой функции класса определите возвращаемый результат:
>function recA.getVal(field: integer); string;
>begin
> case field of
> 1: getVal := intToStr(this);
> 2: getVal := that;
> 3: getVal := intToStr(the_other);
> end;
>end;
Затем вы можете определить
>function myFunc(rec: tAllrecs; field: integer);
>begin
>label2.caption := allrecs.getVal(field);
>end;
затем вы можете вызвать myFunc с любым классом, производным от tAllrecs, например:
>myFunc(recA, 2);
>myFunc(recB, 29);
(getVal предпочтительно должна быть процедурой (а не функцией) с тремя var-параметрами, возвращающими имя, тип и значение.)
Все это работает, т.к. данный пример я взял из моего рабочего проекта.
[Sid Gudes, cougar@roadrunner.com]
Если вы хотите за один раз передавать целую запись, установите на входе ваших функций/процедур тип 'array of const' (убедитесь в правильном приведенни типов). Это идентично 'array of TVarRec'. Для получения дополнительной информации о системных константах, определяемых для TVarRec, смотри электронную справку по Delphi.
Указатели
Указатель на функцию I