我有很多旧的代码使用旧式的pascal对象类型,我试图在Delphi 2009中工作。它编译,但似乎有几个问题处理虚拟方法。看来这个问题已经有关Quality Central的报道了:
http://qc.embarcadero.com/wc/qcmain.aspx?d=71723
我希望仍然使用这些的人(PatrickvL可能?)可以回复更多信息。我们有很多使用对象的代码,如果不能修复,我们就会陷入困境。提前谢谢!
答案 0 :(得分:7)
如果您正在使用虚拟方法,那么您通过引用清楚地访问对象,而不是通过值。这就是类在Delphi中的运行方式,因此切换到类不应该太难。
对于不具有虚拟方法的任何对象类型,您应该能够将它们转换为记录。现在允许记录具有方法,以及可见性说明符。但是,不支持继承。
自1994年2月14日(第一版Delphi的发布日期)以来,旧式对象已被弃用。从那以后,它们一直在恶化。你应该在几年前离开他们。
答案 1 :(得分:3)
我必须承认我有几个啤酒在看这个,只是为了挑战:)你需要一些神奇的字节。根据图例,如果使用任何虚拟方法,旧样式对象仅为指针创建空间。没有虚拟方法没有VMT。
对于新的样式对象,VMT指针始终是第一个,因为它们都声明了虚拟方法。似乎有人忘记了使用旧式对象,VMT可以稍后出现。所以假设它只有一个指针,这使它可以在我的D2009上运行。我不是编译器的胆量,一个叫Dave Jewell的人曾经为PC专业人员写过,可能会证明这一点会稳定......
Type
PObject1 = ^TObject1;
TObject1 = Object
Magic: Array[0..3] of Byte; //or integer or whatever I was playing with the size
FCount : Integer;
Constructor Init;
Procedure Add; virtual;
Procedure Deduct; virtual;
end;
Type
PObject2 = ^TObject2;
TObject2 = Object(TObject1)
Constructor Init;
end;
然后在施工后这些工作:
.
.
.
Object2^.Add;
Object2^.Deduct;
我得到了适当的控制台输出
我添加了一个额外的proc,以确保它适用于2个虚拟:)
顺便说一下,无论你是否把2009年的^知道你的意思,他们都会工作:(
缺少来自embracodeland的正确修复您仍然可能仍需要更改每个BASE对象定义。希望你能找到并插入/替换或Grep ...祝你好运。
答案 2 :(得分:3)
好的 - 完成 - 我无法让它失败......你的D2009是否完全打补丁? 项目/编译器选项?
为了绝对的确定性和比较,这里是我的单位:
---------------项目档案
program testD2009;
{$APPTYPE CONSOLE}
uses
SysUtils,
Object1U in 'Object1U.pas',
Object2U in 'Object2U.pas';
Var
Object1 : PObject1;
Object2 : PObject2;
begin
try
Object1 := New(PObject1,Init);
Object1^.Add;
Object1^.Deduct;
Object2 := New(PObject2,Init);
Object2^.Add;
Object2^.Deduct;
readln;
except
on E:Exception do
Writeln(E.Classname, ': ', E.Message);
end;
end.
-------------- Object1 unit
unit Object1U;
interface
uses SysUtils;
Type
PObject1 = ^TObject1;
TObject1 = Object
Magic: Array[0..3] of Byte;
FCount : Integer;
Constructor Init;
Procedure Add; virtual; { removing virtual allows the program to run }
Procedure Deduct; virtual; { removing virtual allows the program to run }
end;
implementation
Procedure TObject1.Add;
begin
Writeln('Object1 Add');
end;
procedure TObject1.Deduct;
begin
Writeln('Object1 Deduct');
end;
Constructor TObject1.Init;
begin
inherited;
FCount := 0;
Writeln('TObject1 Init');
end;
end.
----------------对象2单元
unit Object2U;
interface
uses Object1U;
Type
PObject2 = ^TObject2;
TObject2 = Object(TObject1)
Constructor Init;
Procedure Add; virtual; { removing virtual allows the program to run }
Procedure Deduct; virtual; { removing virtual allows the program to run }
end;
implementation
procedure TObject2.Add;
begin
Writeln('Object2 Add');
inherited;
end;
procedure TObject2.Deduct;
begin
Writeln('Object2 Deduct');
inherited;
end;
Constructor TObject2.Init;
begin
Inherited Init;
fCount := 1;
Writeln('TObject2:Init');
end;
end.
----------------节目输出:
TObject1 Init Object1 Add Object1 Deduct TObject1 Init TObject2:Init Object2 Add Object1 Add Object2 Deduct Object1 Deduct
我很困惑:)。
答案 3 :(得分:2)
我发送了一封电子邮件给Embarcadero当地的代表处理这个问题,并将他们转介给质量中心的报告。他们基本上告诉我们将所有对象移到课堂上,所以我猜他们并没有计划修复这个......永远。我想我们已经非常接受,如果我们想要继续前进,这就是我们必须要做的事情,所以现在我们必须安排这项工作才能继续升级到Delphi 2009.
只是想感谢所有试图提供帮助的人,但我相信这是一个失败的原因: - (