Autor Beitrag
Geri
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starontopic star
Beiträge: 78

XP
RAD Studio XE pro
BeitragVerfasst: So 30.11.08 13:00 
Hallo zusammen

Ich habe eine Klassendefinition mit :

ausblenden Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
16:
17:
18:
19:
20:
21:
22:
23:
24:
25:
26:
27:
28:
29:
Type
  TBaseClass = class
                 Constructor Create();
               End;

  TTestClassA(TBaseClass)
                 Constructor Create();
               End;

  TTestClassB(TTestClassA)
                 Constructor Create();
               End;

Procedure TestClass(L:TList);
var El:TBaseClass;
    TC:TTestClass;
Begin
  El:=L[0];
  if (El is TTestClassA) then
  Begin
    ..
  End
  else
  if (El is TTestClassB) then
  Begin
    ...
  End

End;


Gerne möchte ich in der Prozedur TestClass mit Hilfe des is-Operators herausfinden um welche Klasse es sich handelt. Bei einm anderen Programm (auf einem anderen PC) ist mir das gelungen.

Wenn ich das Programm im Debugger durchsteppe und an der Stelle
if (El ist TTestClassA) mir im Debugger den Klassennamen anschauen will, dann steht für den Watch-Ausdruck

El.Classnae : Nicht verfügbarer Wert und die Klasse TTestClassB wird nie erkannt.


Wenn ich den Klassenanme zuerst als String auslese und dann Prüfe, dann funktioniert es:

s:String;
s:=El.Classname;
if s = 'TTestClassB' then
Begin
...
end;

Erkennt ihr vielleicht das Problem hier? Liegt es etwa an betimmten IDE-Einstellungen?

Vielen Dank für Eure Hilfe
Geri
PS: Ich verwende Delphi 2005, personal
jakobwenzel
ontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic starofftopic star
Beiträge: 1889
Erhaltene Danke: 1

XP home, ubuntu
BDS 2006 Prof
BeitragVerfasst: So 30.11.08 13:09 
Jede TestClassB ist auch eine TestClassA.
Deshalb wird bei den TestClassBs auch der Code für TestClassA ausgeführt, und der else-Zweig wird gar nicht mehr aufgerufen.

_________________
I thought what I'd do was, I'd pretend I was one of those deaf-mutes.
Geri Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starontopic star
Beiträge: 78

XP
RAD Studio XE pro
BeitragVerfasst: So 30.11.08 13:19 
Hallo Jakob

Vielen Dank für Deinen Hinweis. Das ist sehr interessant.

Ich habe aber ein Programm mit ähnlicher Klassendefinition, dort arbeite ich exzessiv mit dem is-Operator und dieses Problem existiert komischerweise nicht oder mir ist es bisher nicht als Bug aufgefallen

Ich habe das Problem nun mit

if El.Classtype = TTestClassA then ...

gelöst. Das funktioniert

Gibt es dazu noch eine bessere Lösung?

Beste Grüsse

Geri
jakobwenzel
ontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic starofftopic star
Beiträge: 1889
Erhaltene Danke: 1

XP home, ubuntu
BDS 2006 Prof
BeitragVerfasst: So 30.11.08 13:31 
Also mit folgendem Code:
ausblenden volle Höhe Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
16:
17:
18:
19:
20:
21:
22:
23:
24:
25:
26:
27:
28:
29:
30:
31:
32:
33:
34:
35:
36:
37:
38:
39:
40:
41:
42:
43:
program Project1;

{$APPTYPE CONSOLE}
Type
  TBaseClass = class
               End;

  TTestClassA = class(TBaseClass)
               End;

  TTestClassB=class(TTestClassA)
               End;

function TestClass(el:TBaseClass):String;
Begin
  if (El is TTestClassA) then
  Begin
    result:='TTestClassA';
  End
  else
  if (El is TTestClassB) then
  Begin
    result:='TTestClassB';
  End else
    result:='Other';

End;

var
  c:TBaseClass;
begin
  { TODO -oUser -cConsole Main : Hier Code einfügen }
  c:=TBaseClass.Create;
  writeln('TBaseClass: '+TestClass(c)); //Ausgabe: TBaseClass: Other
  c.Free;
  c:=TTestClassA.Create;
  writeln('TTestClassA: '+TestClass(c)); //Ausgabe: TTestClassA: TTestClassA
  c.Free;
  c:=TTestClassB.Create;
  writeln('TTestClassB: '+TestClass(c)); //Ausgabe: TTestClassB: TTestClassA
  c.Free;
  ReadLn;
end.

Krieg ich 2 mal TTestClassA als Ausgabe.
Wenn du bei der If-Abfrage zuerst auf TTestClassB und dann auf TTestClassA prüfst, würde es perfekt gehen.

_________________
I thought what I'd do was, I'd pretend I was one of those deaf-mutes.
Geri Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starontopic star
Beiträge: 78

XP
RAD Studio XE pro
BeitragVerfasst: So 30.11.08 14:01 
Hallo Jakob

Vielen Dank für Deine sehr ausführliche Darstellung des Problems und er Lösung! Das finde ich sehr nett!

Ja, du hast recht, wenn ich zuerst nach TTestClassB abfragen würde dann würde es klappen. Mir gefältt aber der Einsatz

ausblenden Delphi-Quelltext
1:
2:
3:
4:
if (El.ClassType = 'TTestClassB) then
Begin
  ..
End;


besser, weil er keine Ordnung der Abfrage voraussetzt.

Offen bleibt für mich aber noch wieso man beimn Watch-Ausdruck El.ClassName im Debug-Fenster die Ausgabe "nicht verfügbarer Wert" erhält. Hat das vielleicht etwas mit der internen Codeoptimierung zu tun. Ich habe alle mir bekannten Debug-Schalter eingeschaltet und Codeoptimierung ausgeschaletet...:)

Beste Grüsse

Geri