我想实现动态的 Tfn = procedure(t: Integer) of object;方法,要怎么实现procedure TForm1.Button1Click(Sender: TObject);
begin
f(123);//为什么返回 0
exec( @test1 ); //报地址错误
end;各们高手们忙看一下,谢谢unit Unit1;interfaceuses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls;type
Tfn = procedure(t: Integer) of object;
TPfn= ^Tfn;
TForm1 = class(TForm)
Button1: TButton;
procedure Button1Click(Sender: TObject);
procedure FormCreate(Sender: TObject);private
{ Private declarations }
public
{ Public declarations } end;var
Form1: TForm1;
f:Tfn;
procedure test1(t: integer);
procedure exec(fn:Tpfn);
implementation{$R *.dfm}procedure test1(t: integer);
begin
showmessage( intTostr(t));
end;procedure TForm1.FormCreate(Sender: TObject);
begin
@f:=@test1;
end; procedure exec(fn:Tpfn);
begin
fn^(99);
end;procedure TForm1.Button1Click(Sender: TObject);
begin
f(123);
exec( @test1 );
end;end.
begin
f(123);//为什么返回 0
exec( @test1 ); //报地址错误
end;各们高手们忙看一下,谢谢unit Unit1;interfaceuses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls;type
Tfn = procedure(t: Integer) of object;
TPfn= ^Tfn;
TForm1 = class(TForm)
Button1: TButton;
procedure Button1Click(Sender: TObject);
procedure FormCreate(Sender: TObject);private
{ Private declarations }
public
{ Public declarations } end;var
Form1: TForm1;
f:Tfn;
procedure test1(t: integer);
procedure exec(fn:Tpfn);
implementation{$R *.dfm}procedure test1(t: integer);
begin
showmessage( intTostr(t));
end;procedure TForm1.FormCreate(Sender: TObject);
begin
@f:=@test1;
end; procedure exec(fn:Tpfn);
begin
fn^(99);
end;procedure TForm1.Button1Click(Sender: TObject);
begin
f(123);
exec( @test1 );
end;end.
解决方案 »
- 如何防止同一目录下的EXE文件执行两次
- 多线程程序不能断点调试?运行之后不会触发
- 在delphi 中,用ADO ,在前台如何把一外ADO 数据集中的数据全部复制到另外一个ado 数据集中
- 在DELPHI中,如何用ADO连接EXCEL文件,如何访问、编辑Sheet?
- 有没有办法不让TREEVIEW展开和缩放
- 200分寻找一部影片
- SQL数据客户端驱动程序如何自已打包?
- 谁能够给我提供一份使用Delphi语言封装Socket的COM组件??
- 关于TDateTimePicker的问题,请指教!
- 为何我下的例子在设计时不能改变窗体的大小,如何解决?
- 用定时器计算时间之差准吗?
- 可否谈一下Delphi编译器大致是如何把Delphi源代码编译成目标代码的?
要将清楚的话,恐怕几页纸也讲不清楚,我写了一个详细的例子
仔细看清楚test1与test2的定义有什么区别,以及三个按钮的程序
unit Unit1;interfaceuses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls;type
Tfn = procedure(t:integer) of object;
pfn = ^TMethod;
TForm1 = class(TForm)
Button1: TButton;
Button2: TButton;
Button3: TButton;
procedure Button1Click(Sender: TObject);
procedure test1(t:integer);
procedure Button2Click(Sender: TObject);
procedure Button3Click(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
end;
procedure test2(Self : TObject;t:integer);var
Form1: TForm1;
implementation{$R *.dfm}
procedure test2(Self : TObject;t:integer);
begin
showmessage( intTostr(t));
end;procedure Tform1.test1(t: integer);
begin
showmessage( intTostr(t));
end;procedure TForm1.Button1Click(Sender: TObject);
var
f:pfn;
begin
new(f);
f^.Data:=self;
f^.Code:[email protected];
Tfn(f^)(88);end;procedure TForm1.Button2Click(Sender: TObject);
var
f:tfn;
r:tmethod;
begin
r.Data:=self;
r.Code:[email protected];
f:=tfn(r);
f(87);
end;procedure TForm1.Button3Click(Sender: TObject);
var
f:tfn;
r:tmethod;
begin
r.Data:=self;
r.Code:=addr(test2);
f:=tfn(r);
f(86);
end;end.
http://topic.csdn.net/t/20030402/10/1607626.htmlPS:景仰一下alphax(豪言壮语的乌鸦)和老达摩,
Procedure就是可执行的一段程序。Method 其实也就是Procedure,只是他们是属于Object的,可自由的存取 Object内的资源,但它们不能独立于 Object 外,也就是说该Object要被被 Create 了才可使用。到底为什么Method可以存取Object的资源呢?
原來,所有Method都有一个隐藏的第一参数就是Self ,而且当Method存取object的资料時,会先自动到Self 去找,找不到才到Globel去找。另外Method的定义比一般的Procedure多了一個参数就是Self,这个参数就是当Method被呼叫时自动变成第一个参数的值。TMethod 的定义如下 :
TMethod = record
Code : Pointer; // 执行程序的(相当于Procedure)的Pointer
Data : Pointer; // Self的Pointer
end;
所以要一般procedure要变成Method 就要从下面两点入手:1. Self 参数
由于调用Method时是会自动传递Self作为第一个参数的,而其他的参数就要顺移一位,Method 也会自动在最前接收Self这个参数。但Procedure没有这个机制,我们只好自己动手帮它定义这个参数,这就是为什么test2要定义为procedure test2(Self : TObject;t:integer); 的原因
也是test1不要Self : TObject;参数的原因2. 转换为TMethod格式
我们只要建立一个TMethod, 將Procedure的pointer传给TMethod.Code 再把Object传给TMethod.Data 就可以了
TPfn= ^Tfn;
@f:=@test1;
f(123); // 肯定会报错的, Tfn = procedure(t: Integer) of object; 改成
Tfn = procedure(t: Integer);那个指针纯粹多余的
procedure exec(fn: Tfn);
begin
fn(99);
end;procedure TForm1.Button1Click(Sender: TObject);
begin
exec(test1);
end;