我的问题非常简单。 我有一个dwsUnit,它有这段代码:
type
TPointCoord = record
X: Float;
Y: Float;
Z: Float;
end;
type
TMyClass = class
private
fPosition: TPointCoord;
function GetPosition: TPointCoord;
procedure SetPosition(Val: TPointCoord);
public
property Position: TPointCoord read GetPosition write SetPosition;
constructor Create;
end;
function TMyClass.GetPosition: TPointCoord;
begin
Result := fPosition;
end;
procedure TMyClass.SetPosition(Val: TPointCoord);
begin
fPosition := Val;
end;
constructor TMyClass.Create;
begin
inherited Create;
fPosition.X := 1;
fPosition.Y := 2;
fPosition.Z := 3;
end;
var
mc: TMyClass;
begin
mc := TMyClass.Create;
mc.Position.X := 2; //Syntax Error
end.
在mc.Position.X(或Position.Y或Z),我得到:
Syntax Error: Cannot assign a value to the left-side argument [line: 42, column: 17]
这是什么意思?如果是属性,记录是只读的吗? 我如何从Delphi Side访问它。 (第二个问题,不是什么大问题)
答案 0 :(得分:1)
虽然LHirstov代码可以与DWScript一起使用,但是相同的特定代码可能无法与某些旧版本的Delphi一起使用。
因此,对于那些使用旧版Delphi的人,我建议只是向TmyClass添加更多属性,而不是修改记录。
您需要的只是添加三个新属性(每个位置参数一个),然后定义其Getter / Setter方法以单独修改这些特定参数。
type
TPointCoord = record
X: Float;
Y: Float;
Z: Float;
end;
TMyClass = class
private
fPosition: TPointCoord;
function GetPosition: TPointCoord;
function GetPositionX: Float;
function GetPositionY: Float;
function GetPositionZ: Float;
procedure SetPosition(Val: TPointCoord);
procedure SetPositionX(Val: Float);
procedure SetPositionY(Val: Float);
procedure SetPositionZ(Val: Float);
public
property Position: TPointCoord read GetPosition write SetPosition;
property PositionX: TPointCoord read GetPositionX write SetPositionX;
property PositionY: TPointCoord read GetPositionY write SetPositionY;
property PositionZ: TPointCoord read GetPositionZ write SetPositionZ;
constructor Create;
end;
function TMyClass.GetPosition: TPointCoord;
begin
Result := fPosition;
end;
procedure TMyClass.SetPosition(Val: TPointCoord);
begin
fPosition := Val;
end;
function TMyClass.GetPositionX: Float;
begin
Result := fPosition.X;
end;
procedure TMyClass.SetPositionX(Val: Float);
begin
fPosition.X := Val;
end;
function TMyClass.GetPositionX: Float;
begin
Result := fPosition.Y;
end;
procedure TMyClass.SetPositionY(Val: Float);
begin
fPosition.Y := Val;
end;
function TMyClass.GetPositionX: Float;
begin
Result := fPosition.Z;
end;
procedure TMyClass.SetPositionZ(Val: Float);
begin
fPosition.Z := Val;
end;
然后最后使用以下方法访问特定的位置参数:
mc.PositionX := 2;
现在你可能会问自己我还需要旧的Position属性。虽然您在技术上并不需要它,但当您需要整体读取或写入位置记录时它仍然可以派上用场。
答案 1 :(得分:1)
出现此错误的原因是因为您使用的是记录类型的属性。
记录类型是一种值类型,这意味着它在赋值时被复制而不是被引用(如类),因此返回记录的函数(或属性)将复制并返回不同的记录。
所以你的行
mc.Position.X := 2
实际上等同于
temp := mc.getPosition;
temp.X := 2;
“temp”是与fPosition不同的变量/存储,因此代码不会改变fPosition.X,它只会是“隐藏”临时副本的X字段。
由于这通常不太可能是您所追求的,DWS编译器就像Delphi一样,会抛出错误。
典型的解决方案是提供一个独特的PositionX属性,它将提供对fPosition的X字段的访问,如
property PositionX : TPointCoord read (FPosition.X) write (FPosition.X);
或者您可以使用显式的getter / setter,如果您需要的不仅仅是指定的X字段。
另一种解决方案是使用引用类型(类f.i.),尽管这对位置或坐标可能不太实用。
答案 2 :(得分:0)
您拥有TPointCoord类型的属性,并且您只想分配X coord,这就是您遇到错误的原因。如果要分别处理X,Y和Z,则必须为每个属性分配属性。这是X的一个例子:
type
TPointCoord = record
private
fX: real;
fY: real;
fZ: real;
function GetX: real;
procedure SetX(value: real);
public
property X: real read GetX write SetX;
end;
function TPointCoord.GetX: real;
begin
Result:=fX;
end;
procedure TPointCoord.SetX(value: Real);
begin
fX:=Value;
end;
通过上面的示例,您的声明mc.Position.X := 2;
就可以了。