Einzelnen Beitrag anzeigen

Der_Unwissende

Registriert seit: 13. Dez 2003
Ort: Berlin
1.756 Beiträge
 
#4

Re: Inhalte zweier Memos synchron halten

  Alt 18. Mär 2007, 17:11
Zitat von msgroup:
wenn ich zwei Memo's sychron halten möchte, d.h. egal in welchem ich was eingebe - der Inhalt ändert sich sofort in beiden - so sollte dies doch für mein Verständis mit nem Zeiger funzen
Hi,
leider irrst Du Dich etwas (wie Du ja schon gemerkt hast).
Da ein Zeiger immer eine Adresse speichert hast Du nicht unrecht, dass Deine Zuweisung dafür sorgt, dass sowohl die Eigenschaft Lines von memo1 als auch memo2 auf das gleiche TStrings Objekt zeigen.
An dieser Stelle sei aber auch gleich gesagt, dass Du dafür keinen Zeiger benötigst. Bei TStrings handelt es sich um eine Klasse. Alle Instanzen solcher Klassen (Objekte), werden automatisch als Referenz abgespeichert, dass heißt, Du verwendest automatisch (und für Dich transparent) einen typisierten Zeiger.

Delphi-Quellcode:
var x: TStrings;
begin
  x := memo1.Lines;
  // in x steht nun eine Referenz auf die Lines
  // von memo1, x hat also die Größe von 4 Byte
  // egal wie das Objekt, dass Referenziert wird
  // gefüllt ist
end;
Insbesondere wird dieses Verhalten deutlich, wenn Du nun eine solche Referenz an eine Methode als Argument übergibst. Alle Änderungen (z.B. an einem TStrings-Objekt oder einer TBitmap), wirken sich direkt auf das übergebene Objekt und nicht auf eine Kopie aus!

Du führst hier also eigentlich nur eine weitere Indirektion ein, hast also einen expliziten Zeiger, der auf einen impliziten Zeiger zeigt.

An sich ist aber die Zuweisung aus einem anderen Grund problematisch. Hinter der Eigenschaft Lines steckt ein spezielles Objekt, dass an das jeweilige Memo gebunden ist. Die Änderungen an diesem TStrings-Objekt führen zu einer Benachrichtigung des Memos. Die Zuordnung welches Memo hier übergeordnet ist, ist aber eindeutig. Wann genau diese Zuordnung statt findet kann ich nicht sagen, denke aber, dass dies schon beim Erstellen des Memos geschieht.
Setzt Du jetzt also die Eigenschaft Lines von Memo2 auf den Wert Memo1.Lines, dann änderst Du zwar wirklich die Lines-Eigenschaft, aber es wird somit nur noch Memo1 über Änderungen informiert. Die Zeilen
Delphi-Quellcode:
  memo2.Lines := memo1.Lines;
  memo2.Lines.Add('TEST');
dürfte zu einem etwas überraschendem Verhalten führen, der String 'TEST' wird wohl im memo1 angzzeigt. Das liegt einfach daran, dass wirklich beide Memos das gleiche Objekt verwenden. Dieses ist aber (durch einen internen Zustand) fest an Memo1 gebunden. Änderungen an diesem Lines-Objekt führen zu einer Benachrichtigung von Memo1, dass daraufhin sich selbst neu zeichnet. Dadurch, dass Du hier die TStrings-Eigenschaft von memo2 überschrieben hast, ist eine direkt Manipulation vom memo2 nicht mehr möglich.

Möchtest Du alle Werte von einem Memo in das andere übertragen, so solltest Du statt dessen auf die Methode Assign zurück greifen. Diese erledigt für Dich genau diese Übertragung:
Delphi-Quellcode:
  memo2.Lines.beginUpdate;
  memo2.Lines.Assign(memo.Lines);
  memo2.Lines.endUpdate;
Das beginUpdate und endUpdate ist eventuell unnötig, ich bin mir hier nicht sicher, ob Assign diese Methoden automatisch aufruft. Mit BeginUpdate kündigt man mehrere Änderungen an, dass führt dazu, dass die Komponente Änderungen ohne Benachrichtigung durchführt. Erst wenn das endUpdate aufgerufen wird, wird die Komponente wieder aktualisiert und kann alle Änderungen in einem Schritt berücksichtigen.

Gruß Der Unwissende
  Mit Zitat antworten Zitat