AGB  ·  Datenschutz  ·  Impressum  







Anmelden
Nützliche Links
Registrieren
Thema durchsuchen
Ansicht
Themen-Optionen

Pointeradresse auslesen

Ein Thema von paul.kunig · begonnen am 11. Sep 2019 · letzter Beitrag vom 21. Sep 2019
Antwort Antwort
paul.kunig

Registriert seit: 25. Sep 2017
42 Beiträge
 
Delphi 10.3 Rio
 
#1

Pointeradresse auslesen

  Alt 11. Sep 2019, 10:38
Delphi-Version: 5
Hallo zusammen,

folgender Code:
Delphi-Quellcode:
procedure TForm1.Button1Click(Sender: TObject);
var
  Eingabe: ^String;
begin
  New(Eingabe);
  Eingabe^ := Edit1.Text;

  ShowMessage(Eingabe^ + #13#10 +
  IntToStr(Integer(Eingabe)) + #13#10 +
  IntToStr(Integer(@Eingabe)) + #13#10 +
  IntToStr(Integer(Addr(Eingabe)))
  );

  Dispose(Eingabe);
end;
Führe ich das Ganze aus, erhalte ich folgende Werte:
1) Inhalt des Eingabefeldes
2) Einen Dezimalwert, der auch unter lokale Variablen in der Entwicklungsumgebung als Hexadezimalwert angezeigt wird.
3) Einen siebenstelligen Integer
4) Den selben Integer wie in Punkt 3.

Welcher von diesen Werten ist nun die Speicheradresse des Zeigers und woher kommt der verbliebene Wert?

Gruß
Paul
  Mit Zitat antworten Zitat
Amateurprofi

Registriert seit: 17. Nov 2005
Ort: Hamburg
1.087 Beiträge
 
Delphi XE2 Professional
 
#2

AW: Pointeradresse auslesen

  Alt 11. Sep 2019, 11:44
Siehe eingefügte Kommentare im Code
Delphi-Quellcode:
var
   Eingabe: ^String;
begin
   New(Eingabe);
   Eingabe^ := Edit1.Text;

   ShowMessage(Eingabe^ + #13#10 + // Der Text aus dem Edit nach Eingabe kopierte Text
   IntToStr(Integer(Eingabe)) + #13#10 + // Adresse des mit New allozierten Speicherbereichs
   IntToStr(Integer(@Eingabe)) + #13#10 + // Adresse der Variablen "Eingabe"
   IntToStr(Integer(Addr(Eingabe))) // dto
   );

   Dispose(Eingabe);
end;
Gruß, Klaus
Die Titanic wurde von Profis gebaut,
die Arche Noah von einem Amateur.
... Und dieser Beitrag vom Amateurprofi....
  Mit Zitat antworten Zitat
paul.kunig

Registriert seit: 25. Sep 2017
42 Beiträge
 
Delphi 10.3 Rio
 
#3

AW: Pointeradresse auslesen

  Alt 11. Sep 2019, 12:00
Hallo Amateurprofi,

danke für deine Antwort. Noch einmal zum Verständnis.

Die Variable "Eingabe" ist eine Typisierter Zeiger.
In diesen Speicherbereich wird der Wert aus dem Eingabefeld gespeichert.

Also sollte ich zwei Werte abrufen können.
1) Den Werte der unter dieser Speicheradresse abgelegt ist.
2) Die Adresse wo der Wert abgelegt ist.

Aus welchem Grund sollte die Variable "Eingabe", die ja ein Zeiger ist, erneut eine Speicheradresse bekommen?

Gruß
Paul
  Mit Zitat antworten Zitat
Amateurprofi

Registriert seit: 17. Nov 2005
Ort: Hamburg
1.087 Beiträge
 
Delphi XE2 Professional
 
#4

AW: Pointeradresse auslesen

  Alt 11. Sep 2019, 12:24
Hallo Amateurprofi,
Also sollte ich zwei Werte abrufen können.
1) Den Werte der unter dieser Speicheradresse abgelegt ist.
2) Die Adresse wo der Wert abgelegt ist.
Aus welchem Grund sollte die Variable "Eingabe", die ja ein Zeiger ist, erneut eine Speicheradresse bekommen?

Gruß
Paul
Zu 1) und 2):
Kannst und machst Du doch
1) Den Werte der unter dieser Speicheradresse abgelegt ist. Eingabe^ .
2) Die Adresse wo der Wert abgelegt ist. Eingabe .
3) Aus welchem Grund sollte die Variable "Eingabe", die ja ein Zeiger ist, erneut eine Speicheradresse bekommen?
Weil Du mit New(Eingabe) diesen Speicherbereich allozierst und die Adresse dieses Speicherbereichs in Eingabe stellst.

Das New und Dispose kannst Du auch weglassen, indem Du Eingabe als String deklarierst also:
var Eingabe:String; und Eingabe:=Edit1.Text;
Gruß, Klaus
Die Titanic wurde von Profis gebaut,
die Arche Noah von einem Amateur.
... Und dieser Beitrag vom Amateurprofi....
  Mit Zitat antworten Zitat
paul.kunig

Registriert seit: 25. Sep 2017
42 Beiträge
 
Delphi 10.3 Rio
 
#5

AW: Pointeradresse auslesen

  Alt 11. Sep 2019, 13:54
Ich möchte den Wert des Eingabefeldes im Heap speichern, daher der Typisierte Zeiger.

Um den Wert aus dem Speicherbereich auszulesen wird dieser dereferenziert, also Eingabe^.
Um die Speicheradresse auszulesen wird @ oder Addr() verwendet.

So weit, so gut.

Wenn ich den Zeiger nicht mit New() erzeuge, gibt es eine Zugriffsverletzung.
Also ist diese Speicherzuweisung notwendig.

Wozu sollte noch eine Adresse für ein und die selbe Variable, in diesem Fall ein Zeiger, benötigt werden.

Wobei diese anscheinend in verschiedenen Bereichen des Speichers abgelegt sind.
Adresse des Zeigers = achtstellig.
Adresse der Variable, die ja der Zeiger ist = siebenstellig.

Es erschließt sich mir nicht, warum die Adresse eines Zeigers in einer Variable gespeichert werden soll, obwohl der Zeiger selber die Möglichkeit bietet sich selber auszulesen.

Was übersehe ich?
  Mit Zitat antworten Zitat
Amateurprofi

Registriert seit: 17. Nov 2005
Ort: Hamburg
1.087 Beiträge
 
Delphi XE2 Professional
 
#6

AW: Pointeradresse auslesen

  Alt 11. Sep 2019, 14:51
Zunächst mal:
Wir sprechen über Delpi 5, wenn ich #1 richtig interpretiere, also String = ShortString.

Zitat:
Ich möchte den Wert des Eingabefeldes im Heap speichern, daher der Typisierte Zeiger.
.
Was aber aus #1 nicht hervorgeht.

Zitat:
Wenn ich den Zeiger nicht mit New() erzeuge, gibt es eine Zugriffsverletzung.
Also ist diese Speicherzuweisung notwendig.
.
Ja, wenn "Eingabe" als ^String deklariert ist, ist das so.

Zitat:
Wozu sollte noch eine Adresse für ein und die selbe Variable, in diesem Fall ein Zeiger, benötigt werden.
.
"Eingabe" ist die Variable, in der die Adresse des allozierten Speicherbereiches steht.
Der Inhalt von "Eingabe" ist diese Adresse.
Also: Die Variable "Eingabe" und die Adresse des allozierten Speicherbereiches sind nicht dasselbe.
Egal, ob du den Speicher mit New(Eingabe) oder z.B. mit GetMem(Eingabe, SizeOf(String)) allozierst, brauchst du einen Ort, wo die Adresse des allozierten Speichers gespeichert wird

Zitat:
Wobei diese anscheinend in verschiedenen Bereichen des Speichers abgelegt sind.
Adresse des Zeigers = achtstellig.
Adresse der Variable, die ja der Zeiger ist = siebenstellig.
.
"Eingabe" ist eine lokale Variable, die auf dem Stack angelegt wird.
Der mit New allozierte Speicher liegt dagegen auf dem Heap.
Der Stack wächst von oben nach unten, der Heap aber von unten nach oben.
Heap und Stack sind also unterschiedliche Speicherbereiche.

Zitat:
Es erschließt sich mir nicht, warum die Adresse eines Zeigers in einer Variable gespeichert werden soll, obwohl der Zeiger selber die Möglichkeit bietet sich selber auszulesen.
.
Wie stellst Du Dir denn vor zunächst einen Speicherbereich für den Text zu allozieren und anschließend den Text in diesem zu speichern, wenn Du die Adresse des Speicherbereiches nicht irgendwo speicherst?
Gruß, Klaus
Die Titanic wurde von Profis gebaut,
die Arche Noah von einem Amateur.
... Und dieser Beitrag vom Amateurprofi....
  Mit Zitat antworten Zitat
samso

Registriert seit: 29. Mär 2009
439 Beiträge
 
#7

AW: Pointeradresse auslesen

  Alt 12. Sep 2019, 09:05

Aus welchem Grund sollte die Variable "Eingabe", die ja ein Zeiger ist, erneut eine Speicheradresse bekommen?

Gruß
Paul
Weil der Wert einer Variablen irgendwo gespeichert werden muss. Deshalb hat jede Variable eine Speicheradresse. In Deinem Fall wird der Wert der Variable auf dem Stack gespeichert. Wenn Du noch tiefer einsteigen willst, dann musst Du Dich mit der CPU beschäftigen.
  Mit Zitat antworten Zitat
paul.kunig

Registriert seit: 25. Sep 2017
42 Beiträge
 
Delphi 10.3 Rio
 
#8

AW: Pointeradresse auslesen

  Alt 13. Sep 2019, 13:02
Zuerst einmal Danke für die vielen Antworten.

Jedoch lüftet sich der Schleier nur sehr langsam.

IntToStr(Eingabe^) = Dereferenzierung des Zeigers. Ausgabe des unter der Adresse abgelegten Wertes.

IntToStr(Integer(Eingabe)) // Erwartete Ausgabe
Welche Ausgabe? Es handelt sich um einen Zeiger!

IntToStr(Integer(@Eingabe)) Adresse auf dem Stack.
Warum Adresse des Stacks? Es geht doch um die Adresse des reservierten Speicherplatzes auf dem Heap!

Meines Wissens nach wird der Heap benutzt, wenn größere Datenstrukturen verwendet werden.
Da der Stack in seiner Größe sehr beschränkt ist, weicht man mit Zeigern auf den Heap aus.

Das heißt doch, dass die lokal angelegte Variable lediglich die Adresse des Zeigers, der auf den Heap zeigt, speichert.

Somit müsste man folgende Werte aus der lokalen Variable auslesen können:
1) Adresse der lokalen Variable auf dem Stack
2) Wert der Variable, der in diesem Fall lediglich die Adresse des Zeigers, der auf den Heap zeigt, darstellt.

Ist diese Adresse 4 bzw.8 Byte groß?
Wenn ja, wofür brauchen wir dann den Zeiger, der ja die gleiche Größe hat?

Nach dieser Aufbereitung komme ich zu folgendem Schluss:
IntToStr(Integer(Eingabe))
gibt die eigentliche Adresse des Zeigers auf den Heap zurück, da dies der abgelegte/gespeicherte Wert in der lokalen Variable ist.

IntToStr(Integer(@Eingabe)) als auch
IntToStr(Integer(Addr(Eingabe)))
gibt die Adresse der lokalen Variable zurück, für die im Stack Speicher reserviert wurde, um die Adresse des Zeigers zu speichern.

Dies kommt mir logisch vor, widerspricht aber der bisherigen Dokumentation, in der gesagt wird, dass @ und Addr() die Adresse des Zeigers wiedergeben.
Abschließend sei gesagt, dass nicht näher erläutert ist, welcher Zeiger gemeint ist, da auch die lokale Variable im Hintergrund lediglich ein Zeiger ist.

Gruß und Danke an alle
  Mit Zitat antworten Zitat
Dennis07

Registriert seit: 19. Sep 2011
Ort: Deutschland
491 Beiträge
 
Delphi 11 Alexandria
 
#9

AW: Pointeradresse auslesen

  Alt 20. Sep 2019, 16:28
Nimm statt Integer(MeinZeiger) besser NativeInt(MeinZeiger) oder noch besser dessen Alias IntPtr(MeinZeiger) . Das funktioniert nicht nur unter Win32, sondern auch Win64 und anderen Plattformen.
Dennis
  Mit Zitat antworten Zitat
Benutzerbild von p80286
p80286

Registriert seit: 28. Apr 2008
Ort: Stolberg (Rhl)
6.659 Beiträge
 
FreePascal / Lazarus
 
#10

AW: Pointeradresse auslesen

  Alt 21. Sep 2019, 21:40

Dies kommt mir logisch vor, widerspricht aber der bisherigen Dokumentation, in der gesagt wird, dass @ und Addr() die Adresse des Zeigers wiedergeben.
@ und Addr() liefern beide die Speicheradresse (Pointer) der angesprochenen Variablen.
Mit New(mypointer) reservierst Du Speicher auf dem Heap entsprechend dem Typ auf den mypointer zeigen soll. Weiterhin wird in mypointer die Startadresse des reservierten Speichers abgelegt.

Gruß
K-H

@Sherlock
Gut gebrüllt Löwe. Aber wenn jemand wissen will was es mit Pointern und dem Heap auf sich hat ist das eigentlich positiv zu werten, denn ungesundes Halbwissen auf diesem Gebiet ist tödlich.
Programme gehorchen nicht Deinen Absichten sondern Deinen Anweisungen
R.E.D retired error detector

Geändert von p80286 (21. Sep 2019 um 21:58 Uhr)
  Mit Zitat antworten Zitat
Antwort Antwort


Forumregeln

Es ist dir nicht erlaubt, neue Themen zu verfassen.
Es ist dir nicht erlaubt, auf Beiträge zu antworten.
Es ist dir nicht erlaubt, Anhänge hochzuladen.
Es ist dir nicht erlaubt, deine Beiträge zu bearbeiten.

BB-Code ist an.
Smileys sind an.
[IMG] Code ist an.
HTML-Code ist aus.
Trackbacks are an
Pingbacks are an
Refbacks are aus

Gehe zu:

Impressum · AGB · Datenschutz · Nach oben
Alle Zeitangaben in WEZ +1. Es ist jetzt 22:37 Uhr.
Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz