好像是多态的问题,不懂,帮看看。(50分)

  • 主题发起人 主题发起人 dsuser
  • 开始时间 开始时间
D

dsuser

Unregistered / Unconfirmed
GUEST, unregistred user!
//delphi实例大全一例
unit TestClass;

interface

type
TTest = class
protected
ProtectedData: Integer;
public
PublicData: Integer;
function GetValue: string;
end;

implementation

uses
SysUtils;

function TTest.GetValue: string;
begin
Result := Format ('Public: %d, Protected: %d',
[PublicData, ProtectedData]);
end;

end.
//////////////////////////////////////////////////////////////////////////////
......
uses
TestClass;

procedure TForm1.Button1Click(Sender: TObject);
var
Obj: TTest;
begin
Obj := TTest.Create;
Obj.PublicData := 10;
// Obj.ProtectedData := 20
//won't compile
ShowMessage (Obj.GetValue);
Obj.Free;
end;

type
TFake = class (TTest);

procedure TForm1.Button2Click(Sender: TObject);
var
Obj: TTest;
begin
Obj := TTest.Create;
Obj.PublicData := 10;
TFake (Obj).ProtectedData := 20
// compiles!
ShowMessage (Obj.GetValue);
Obj.Free;
end;

end.
问:注释掉那行为什么//won't compile??
 
不是多态,而是不能访问私有域.
TFake能访问是因为delphi把一个unit内的类当做"友元".
 
protected的描叙:保护元素只能在当前类和它的子类访问,或者当前单元访问。
而一旦将该类放到单独的单元中,就不能从其他单元直接访问他的protected了。
但type
TFake = class (TTest);这句的意思是建立了一个无意义的派生类,对他进行强制类型
转换就可以访问其父类的受保护类型了!也就是可以说TFAKE类和试图访问继承元素中数据
的代码所在单元相同,所以可以访问保护数据,
就是说父类TTest和子类TFake在同一个单元中!
相应的如果把TFake的声明:
type
TFake = class (TTest);放到另一个单元中,则TFake (Obj).ProtectedData := 20
就不会编译通过了。
Good Luck!


 
补充:
1/:类中的保护,私有数据只能由该类的对象方法调用,而不能由实例调用。不能编译的原因就在这。
2:基类A(unit1)在另一个单元中派生出另一个类B(比如 unit2),B继承A后,私有数据不能访问,而保护数据可以访问,意思是说。这种形式的派生产生的类,对基类的私有数据不能修改,而保护数据没此限制。
3:多态简单的说是指一个基类的对象,它既可以调用自己类中的某一对象方法,又可以调用派生类的重载的同一对象方法。
4:TFake (Obj).ProtectedData := 20
// compiles!,这涉及到了友元类的概念。
以上是我的理解。
 
改正一点,4:TFake (Obj).ProtectedData := 20
// compiles!,应该不是友元的概念,它应该遵守的还是第二条所说的。
 
TO:hygsxy
你下面的理解完全错误,建议再看看书:
1/:类中的保护,私有数据只能由该类的对象方法调用,而不能由实例调用。不能编译的原因就在这。


 
我说的是该类,我没有说派生类。网事如风, 老兄看清楚。
TA=Class
provate
x:integer;
end;
var
abc:Ta;
procedure hyg
begin
abc:=Ta.create;
abc.x;//这能调用么?我说的错了么?·!!!!!
end;

 
啊哈,暂且可以称为“友元”,但在Delphi中应该没有这个概念。
 
這樣的問題﹐建議你去找MARCO CANTU的老書《DELPHI高級開發指南》看看。

李維的新書《INSIDE VCL》也提到這個問題。

DEV EXPRESS的組件源代碼就用到這種技朮。

其實﹐講穿了﹐是因為DELPHI在編譯器的實現時就是這么處理的所致﹐就象你的名字一樣﹐
命名了﹐就沒啥理由了。

再者﹐MFC用宏﹐DELPHI用VMT﹐各家的編譯器實現不同而已。不必鑽牛角尖。

﹕)
 
多人接受答案了。
 
后退
顶部