我可以使用指向 Class 的指针吗?
Can I use Pointer to a Class?
我正在使用 Delphi XE3。而在研究了 post Delphi - Maintaining Self References to an Object 之后,我明白了 class 类型的变量实际上是一个引用对象的指针。
因此,我写了下面的代码来测试一下,如下:
TMyClass = class
public
constructor Create(Name: string);
destructor Destroy;
function GetName: string;
private
FName: string;
end;
PMyClass = ^TMyClass;
constructor TMyClass.Create(Name: string);
begin
FName := Name;
end;
destructor TMyClass.Destroy;
begin
end;
function TMyClass.GetName: string;
begin
Result := FName;
end;
procedure TForm1.Button2Click(Sender: TObject);
var
Item: TMyClass;
P: PMyClass;
begin
Item := TMyClass.Create('Jim');
P := PMyClass(Item);
OutputDebugString(PWideChar(Format('Address of object: %x; Address of variable Item: %x; Value of P: %x;',
[Integer(Item), Integer(@Item), Integer(P)])));
OutputDebugString(PWideChar(Format('Name is %s', [Item.GetName()])));
OutputDebugString(PWideChar(Format('Name is %s', [P.GetName()])));
end;
在我的代码中,使用 PMyClass(Item) 似乎也可以获得对象地址,因为 Integer(PMyClass(Item)) 与 Integer(Item) 相同。但是,似乎有了指向对象的指针,我无法调用任何方法,P.GetName() 和 P^.GetName() 都会导致访问冲突。为什么?
我的问题是,我是否可以在编程中使用指向 class 的指针。另外是否有必要使用指向 class 的指针,因为 class 类型的变量已经保存了对象地址。
Item
已经是指向 TMyClass
实例的指针,您不需要引入过多的寻址级别。
NativeInt(Item)
给你地址的数字表示。要通过正确的类型转换从 P
获得相同的表示,您需要使用 P = @Item
和 NativeInt(P^)
我看不出指针对您的任务有何用处....顺便说一句,您真正的问题是什么?
PMyClass(Item)
这个演员是错误的。因为 Item
是 TMyClass
而 PMyClass
是 ^TMyClass
。项目不能同时是 TMyClass
和 ^TMyClass
.
无效的转换是您遇到访问冲突的原因。
如果您确实想要获得一个 ^TMyClass
的值,那么您需要获取一个 TMyClass
值的地址。您的代码中的一个示例是 @Item
。所以,Item
是 TMyClass
,因此 @Item
是 ^TMyClass
。
有些情况下 ^TMyClass
可能有用,但它们在您提供的任何代码中都不明显。例如,您可以使用 ^TMyClass
类型的变量来保存对 TMyClass
类型变量的引用。换句话说,指针有用的标准场景。
我正在使用 Delphi XE3。而在研究了 post Delphi - Maintaining Self References to an Object 之后,我明白了 class 类型的变量实际上是一个引用对象的指针。
因此,我写了下面的代码来测试一下,如下:
TMyClass = class
public
constructor Create(Name: string);
destructor Destroy;
function GetName: string;
private
FName: string;
end;
PMyClass = ^TMyClass;
constructor TMyClass.Create(Name: string);
begin
FName := Name;
end;
destructor TMyClass.Destroy;
begin
end;
function TMyClass.GetName: string;
begin
Result := FName;
end;
procedure TForm1.Button2Click(Sender: TObject);
var
Item: TMyClass;
P: PMyClass;
begin
Item := TMyClass.Create('Jim');
P := PMyClass(Item);
OutputDebugString(PWideChar(Format('Address of object: %x; Address of variable Item: %x; Value of P: %x;',
[Integer(Item), Integer(@Item), Integer(P)])));
OutputDebugString(PWideChar(Format('Name is %s', [Item.GetName()])));
OutputDebugString(PWideChar(Format('Name is %s', [P.GetName()])));
end;
在我的代码中,使用 PMyClass(Item) 似乎也可以获得对象地址,因为 Integer(PMyClass(Item)) 与 Integer(Item) 相同。但是,似乎有了指向对象的指针,我无法调用任何方法,P.GetName() 和 P^.GetName() 都会导致访问冲突。为什么?
我的问题是,我是否可以在编程中使用指向 class 的指针。另外是否有必要使用指向 class 的指针,因为 class 类型的变量已经保存了对象地址。
Item
已经是指向 TMyClass
实例的指针,您不需要引入过多的寻址级别。
NativeInt(Item)
给你地址的数字表示。要通过正确的类型转换从 P
获得相同的表示,您需要使用 P = @Item
和 NativeInt(P^)
我看不出指针对您的任务有何用处....顺便说一句,您真正的问题是什么?
PMyClass(Item)
这个演员是错误的。因为 Item
是 TMyClass
而 PMyClass
是 ^TMyClass
。项目不能同时是 TMyClass
和 ^TMyClass
.
无效的转换是您遇到访问冲突的原因。
如果您确实想要获得一个 ^TMyClass
的值,那么您需要获取一个 TMyClass
值的地址。您的代码中的一个示例是 @Item
。所以,Item
是 TMyClass
,因此 @Item
是 ^TMyClass
。
有些情况下 ^TMyClass
可能有用,但它们在您提供的任何代码中都不明显。例如,您可以使用 ^TMyClass
类型的变量来保存对 TMyClass
类型变量的引用。换句话说,指针有用的标准场景。