我很想知道为什么Delphi将记录类型属性视为只读:
TRec = record
A : integer;
B : string;
end;
TForm1 = class(TForm)
private
FRec : TRec;
public
procedure DoSomething(ARec: TRec);
property Rec : TRec read FRec write FRec;
end;
如果我试图将一个值赋给Rec属性的任何成员,我会得到"Left side cannot be assigned to“错误:
procedure TForm1.DoSomething(ARec: TRec);
begin
Rec.A := ARec.A;
end;
同时也允许对底层字段执行相同的操作:
procedure TForm1.DoSomething(ARec: TRec);
begin
FRec.A := ARec.A;
end;
对这种行为有什么解释吗?
发布于 2009-03-06 22:11:20
由于"Rec“是一个属性,编译器对它的处理稍有不同,因为它必须首先计算属性decl的"read”。考虑这一点,它在语义上与您的示例等效:
...
property Rec: TRec read GetRec write FRec;
...
如果你这样看它,你可以看到对" Rec“的第一个引用(在点”.“之前)必须调用GetRec,这将创建一个Rec的临时本地副本。这些临时文件被设计为“只读”。这就是你要遇到的。
您可以在这里做的另一件事是将记录的各个字段分解为包含类上的属性:
...
property RecField: Integer read FRec.A write FRec.A;
...
这将允许您通过属性直接赋值给类实例中嵌入记录的字段。
发布于 2009-03-06 23:22:29
是的,这是一个问题。但是这个问题可以使用记录属性来解决:
type
TRec = record
private
FA : integer;
FB : string;
procedure SetA(const Value: Integer);
procedure SetB(const Value: string);
public
property A: Integer read FA write SetA;
property B: string read FB write SetB;
end;
procedure TRec.SetA(const Value: Integer);
begin
FA := Value;
end;
procedure TRec.SetB(const Value: string);
begin
FB := Value;
end;
TForm1 = class(TForm)
Button1: TButton;
procedure Button1Click(Sender: TObject);
private
FRec : TRec;
public
property Rec : TRec read FRec write FRec;
end;
procedure TForm1.Button1Click(Sender: TObject);
begin
Rec.A := 21;
Rec.B := 'Hi';
end;
这样编译和工作都没有问题。
发布于 2014-05-05 17:04:13
我经常使用的一种解决方案是将属性声明为指向记录的指针。
type
PRec = ^TRec;
TRec = record
A : integer;
B : string;
end;
TForm1 = class(TForm)
private
FRec : TRec;
function GetRec: PRec;
procedure SetRec(Value: PRec);
public
property Rec : PRec read GetRec write SetRec;
end;
implementation
function TForm1.GetRec: PRec;
begin
Result := @FRec;
end;
procedure TForm1.SetRec(Value: PRec);
begin
FRec := Value^;
end;
这样,直接赋值Form1.Rec.A := MyInteger
将起作用,但Form1.Rec := MyRec
也会按照预期将MyRec
中的所有值复制到FRec
字段中。
这里唯一的缺陷是,当您希望实际检索要使用的记录的副本时,您必须使用类似于MyRec := Form1.Rec^
的命令
https://stackoverflow.com/questions/620506
复制相似问题