【问题标题】:Access a strict protected property of a Delphi class?访问 Delphi 类的严格保护属性?
【发布时间】:2012-01-09 22:17:03
【问题描述】:

我需要访问一个受严格保护的属性,因为我需要创建一个验证(基于此属性的值)以避免出现错误。 (我没有具有此属性的第三方类的源代码)只有我有类(接口)和 dcu 的定义(所以我无法更改属性可见性)。问题是存在访问严格受保护属性的方法吗? (我真的阅读了Hallvard Vassbotn Blog,但我没有找到关于这个特定主题的任何内容。)

【问题讨论】:

  • 您可能可以使用原始内存访问来读取此属性的支持字段。不知道是否有更强大的解决方案。
  • 看起来像班级帮手。

标签: delphi delphi-xe class-helpers


【解决方案1】:

这个类助手示例编译得很好:

type
  TMyOrgClass = class
  strict private
    FMyPrivateProp: Integer;
  strict protected
    property MyProtectedProp: Integer read FMyPrivateProp;
  end;

  TMyClassHelper = class helper for TMyOrgClass
  private
    function GetMyProtectedProp: Integer;
  public
    property MyPublicProp: Integer read GetMyProtectedProp;
  end;

function TMyClassHelper.GetMyProtectedProp: Integer;
begin
  Result:= Self.FMyPrivateProp;  // Access the org class with Self
end;

更多关于类助手的信息可以在这里找到:should-class-helpers-be-used-in-developing-new-code

更新

从 Delphi 10.1 Berlin 开始,使用类助手访问 privatestrict private 成员不起作用。它被认为是一个编译器错误,并已得到纠正。不过,类助手仍然允许访问 protectedstrict protected 成员。

在上面的示例中,说明了对私有成员的访问。下面显示了一个可以访问严格受保护成员的工作示例。

function TMyClassHelper.GetMyProtectedProp: Integer;
begin
  with Self do Result:= MyProtectedProp;  // Access strict protected property
end;

【讨论】:

  • 当类助手在不同的单元中声明时这是否有效?问题涉及严格受保护的成员,确切地说是属性。
  • @DavidHeffernan,好的,我修改了代码以反映严格的受保护属性。是的,它在单独的单元中声明时有效。
  • 非常好。我不得不承认我从来没有使用过类助手。
  • 从 Delphi Berlin 开始,您无法访问私有和受保护的字段。这是一个错误,所以开发。在柏林修好了。所以现在你只能通过继承类来访问受保护的方法。
  • @alitrun,如果您研究对我的回答所做的更新,您会发现仍然可以使用类帮助程序访问受保护的方法。此外,还有另一个技巧可以打开对柏林/东京的私有/受保护字段的访问。只需将其写在一个助手中:with Self do begin { any field/ method is accessible here} end;
【解决方案2】:

您可以使用标准protected hack 的变体。

第一单元

type
  TTest = class
  strict private
    FProp: Integer;
  strict protected
    property Prop: Integer read FProp;
  end;

第 2 单元

type
  THackedTest = class(TTest)
  strict private
    function GetProp: Integer;
  public
    property Prop: Integer read GetProp;
  end;

function THackedTest.GetProp: Integer;
begin
  Result := inherited Prop;
end;

第 3 单元

var
  T: TTest;

....

THackedTest(T).Prop;

严格保护只允许您从定义类和子类访问成员。所以你必须在破解类上实际实现一个方法,将其公开,并使用该方法作为进入目标严格保护成员的路由。

【讨论】:

  • 通常的警告条款包括这一项;当有人修改上游类时,例如当您迁移到新的 delphi 版本,并且 VCL 源发生更改时,您的 Cracker 类将升级为(可能)成为 Crasher 类。
  • @WarrenP 不,事实并非如此。如果破解者曾经是崩溃者,那么使用上游类 untainted 会导致同样的崩溃,
  • 我比类助手解决方案更喜欢这个解决方案,因为它没有类助手的限制。
  • @WarrenP:这个解决方案非常安全,因为继承的类共享原始类的内存布局。 THackedTest 不添加任何变量或虚拟方法。
  • 好的。好吧,那么这可能是一个游戏保护程序。它也可以在 Delphi 7 中使用,而类助手则不能。 +1。
猜你喜欢
  • 1970-01-01
  • 2010-12-03
  • 2016-08-13
  • 2017-10-29
  • 2013-07-19
  • 2012-09-27
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多