Delphi-PRAXiS

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Object-Pascal / Delphi-Language (https://www.delphipraxis.net/32-object-pascal-delphi-language/)
-   -   Delphi Klasse komplett dublizieren (https://www.delphipraxis.net/78741-klasse-komplett-dublizieren.html)

Alexander Roth 10. Okt 2006 14:42


Klasse komplett dublizieren
 
Hallo,

ich weis, ich weis. Das Thema hatten wir schon sehr oft. Ich habe allerdings keine Lösung gefunden die ganz allgemein und für jede Klasse gilt.

Es habe nämlich folgendes Problem: In meinem Programm SolariXX benutze ich die "RiverSoftAVG Charting Component Suite". Wenn ich z.B. nun hineinzoome ist es äußerst schwierig wieder den vorherigen Zustand wiederherzustellen.

Deshalb wäre eine imho elegante Lösung die Klasse temporär zu kopieren und im gegebenen Fall einfach zurück zu kopieren. Doch leider funktioniert Assign nicht und MrSpock's Ansatz (hier) funktioniert irgendwie bei mir auch nicht. Ich glaube jedoch dieser Ansatz ist der erfolgversprechenste.

Deshalb habe ich mir mal ein TestProjekt schnell mal angelegt und irgendwie passiert gar nix.
Also Eine Form mit einem Edit was Temporär kopiert und wiederhergestellt werden soll.
Delphi-Quellcode:
var
  Form1: TForm1;

  ed:Tedit;
implementation

{$R *.dfm}


procedure TForm1.Button1Click(Sender: TObject);
begin
  Move(Pointer(self.Edit1)^, Pointer(ed)^, sizeof(self.Edit1));
end;


procedure TForm1.Button2Click(Sender: TObject);
begin
  Move(Pointer(ed)^, Pointer(self.Edit1)^, sizeof(ed));
end;


procedure TForm1.FormCreate(Sender: TObject);
begin
  ed:=Tedit.Create(self);
end;

procedure TForm1.FormDestroy(Sender: TObject);
begin
  ed.Free;
end;
Was mache ich falsch?
Wieso muss man eigentlich das so schriben: Pointer(ed)^
Was bewirkt das?

Gibt es vielleicht einen einacheren Weg?

Kann man vielleicht die Felder und Propertys einer Klasse ganz allgemein durchlaufen?
Also so was für Felder anstadt Objekten:
Delphi-Quellcode:
    for i:=0 to form1.ComponentCount -1 do
      begin
      if form1.Components[i] is TEdit then
        // do something
      end;
Danke im Voraus

Gruß Alexander

shmia 10. Okt 2006 15:05

Re: Klasse komplett dublizieren
 
1.) wenn du versuchst, ein Objekt mit Move() zu kopieren, wirst du in der :twisted: Hölle :twisted: braten, denn das geht garantiert schief! Objekte werden mehrfach freigeben und es hagelt AVs.
2.) wenn du den Sourcode hast, dann solltest du die Assign-Methode verbessern
3.) wenn du keinen Sourcecode hast, dann schreibst du dir eine Kopierfunktion:
Delphi-Quellcode:
procedure CopyChart(source, dest : TChart);
begin
   // fiktives Beispiel
   dest.zoomfactor := source.zoomfactor;
   dest.height : source.height;
   dest.Font.Assign(source.Font);  // so wird ein enthaltenes Objekt kopiert
   ....
   // es ist mühsam jedes Property runterzuschreiben, aber auf jeden Fall sicher

   // du willst vielleicht nicht alle properties kopieren,
   // deshalb würde ein automatisches Kopieren alle Props nicht sinnvoll sein
end

Alexander Roth 10. Okt 2006 15:21

Re: Klasse komplett dublizieren
 
Zitat:

Zitat von shmia
1.) wenn du versuchst, ein Objekt mit Move() zu kopieren, wirst du in der :twisted: Hölle :twisted: braten, denn das geht garantiert schief! Objekte werden mehrfach freigeben und es hagelt AVs.

Kapiert.

Ich komme dann wohl nicht um die Kopierfunktion herum. Das ist zwar alles andere als:
Zitat:

Zitat von Alexander Roth
die ganz allgemein und für jede Klasse gilt.

Aber na ja.


Wieso hat Borland denn eigentlich so eine wichtige Sache nicht eingebaut? Wieso geht das nicht?!

3_of_8 10. Okt 2006 15:52

Re: Klasse komplett dublizieren
 
Nenn mir mal eine Sprache, in der du jede beliebige Klasse kopieren kannst.

generic 10. Okt 2006 16:29

Re: Klasse komplett dublizieren
 
imho alle .net sprachen

Dax 10. Okt 2006 16:33

Re: Klasse komplett dublizieren
 
Du kannst ein Objekt in .net auch nur dann clonen, wenn es IClonable implementiert oder serialisierbar ([Serializable]) ist. Das is auch nicht überall...

r2c2 10. Okt 2006 16:40

Re: Klasse komplett dublizieren
 
Der Fehler liegt IMHO hier:
Zitat:

Zitat von Alexander Roth
Delphi-Quellcode:
procedure TForm1.Button1Click(Sender: TObject);
begin
  Move(Pointer(self.Edit1)^, Pointer(ed)^, sizeof(self.Edit1));
end;

sizeof(Edit1) gibt immer 4 aus. Warum? Weil n TEdit nur n Pointer is... ggf. könnte es funktionieren, wenn du noch n Pointer()^ mit einbaust. Trotzdem: Wie unser Spitzohriger Mod schon gesagt hat: Mehr als unschön...

Zitat:

Wieso muss man eigentlich das so schriben: Pointer(ed)^
Was bewirkt das?
Das ich Trock 18. So bekommst du ein dereferenziertes Objekt, was eigentlich aus gutem Grund gar nicht geht...

Zitat:

Gibt es vielleicht einen einacheren Weg?

Kann man vielleicht die Felder und Propertys einer Klasse ganz allgemein durchlaufen?
Also so was für Felder anstadt Objekten:
Delphi-Quellcode:
    for i:=0 to form1.ComponentCount -1 do
      begin
      if form1.Components[i] is TEdit then
        // do something
      end;

Guck dir mal RTTI an. Damit könnte das gehen, was du willst...

Zitat:

Zitat von 3_of_8
Nenn mir mal eine Sprache, in der du jede beliebige Klasse kopieren kannst.

u.a. .NET-Sprachen und C++. IMHO. .NET hat MemberwiseClone(damit gehts per Trick 19) und ICloneable(sowas wie Assign bei Delphi) C++ kennt sowas wie Kopierkonstruktoren(und so kranke Konstrukte, wie lokale statische Objekte aufm Stack :freak: )...

mfg

Christian

Der_Unwissende 10. Okt 2006 16:41

Re: Klasse komplett dublizieren
 
Hi,
Sprachen die Reflections unterstützen machen es einem zumindest um einiges leichter. An sich kann man hier natürlich irgendeine Sprache wählen, die man gerade selbst entwickelt, die das kann oder halt etwas wie C (zeig mir das C-Objekt, dass sich nicht clonen lässt). Ob man Klassen clonen kann oder nicht wäre jetzt wohl Ansichtssache, bei den Objekten geht es auf jeden Fall in den weitverbreiteten Sprachen nicht. Dürfte aber schon daran liegen, dass sonst die Schutzklassen sinnlos wären...

Gruß Der Unwissende


Alle Zeitangaben in WEZ +1. Es ist jetzt 10:49 Uhr.

Powered by vBulletin® Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz