![]() |
Pointer/Cardinal-Casterei beenden
Hallo Leute,
habe einen Code wie diesen (bisschen mehr/ bisschen sinnvoller :zwinker: ):
Delphi-Quellcode:
Der besagte Teil macht mir Bauchschmerzen, da ich einen Zeiger in einen Cardinal caste
type PWord = ^word;
TdynArray = class constructor create(size: cardinal); destructor destroy; override; private size: cardinal; data: PWord; public function getWord(index: cardinal): word; end; constructor TdynArray.create(size: cardinal); begin inherited create; getMem(data, size); end; destructor TdynArray.destroy; begin freeMem(data, size); inherited; end; function TdynArray.getWord(index: cardinal): word; begin result := PByte(cardinal(data)+(index shl 1))^; // <= hier ist der böse Code end; :arrow: funktioniert, sieht aber nicht so schick aus und ich weiß nicht, was auf 64-Bit-Maschinen passieren würde :pale: Kennt ihr eine Alternative? MfG, Bug PS: Dynamische Array kommen nicht in Frage, bei Delphi 3 gibt es solchen Luxus noch nicht :-D |
Re: Pointer/Cardinal-Casterei beenden
Delphi-Quellcode:
Dieser Code kompiliert? Gut, dann sollte folgendes auch funktionieren:
function TdynArray.getWord(index: cardinal): word;
begin result := PByte(cardinal(data)+(index shl 1))^; // <= hier ist der böse Code end;
Delphi-Quellcode:
Jedenfalls glaube ich, dass das dann geht.. Hab schon lang nix mehr gepointert ;)
function TdynArray.getWord(index: cardinal): word;
var temp: PByte; begin temp := PByte(data); Inc(temp, index shl 1); result := temp^; end; edit: Was spricht gegen Array[0..0] und ausgeschaltetes Range-Checking? |
Re: Pointer/Cardinal-Casterei beenden
Warum sollte es denn nicht auf 64bit Maschienen funktionieren? Ein Pointer ist genau so groß wie ein Cardinal. D.h. selbst auf 64bit Maschienen solltest du keine Probleme bekommen wegen dem Cardinal (andernfalls würde das ja sonst bedeuten das du auch mit Pointern ein Problem bekommst)
|
Re: Pointer/Cardinal-Casterei beenden
Warum überhaupt PByte? Dadurch muss man überhaupt den Index veroppeln...
Warum nicht einfach:
Delphi-Quellcode:
function TdynArray.getWord(index: cardinal): word;
var lTemp: PWord; begin lTemp := data; Inc(lTemp, index); result := lTemp^; end; |
Re: Pointer/Cardinal-Casterei beenden
Hallo Bug,
solltest du beim Anfordern/Freigeben des Speichers den Wert size nicht mit der Elementgröße (=SizeOf(Word)) multiplizieren? Oder gibt size gar nicht die Anzahl der Elemente sondern die Arraygröße in Bytes an? Das interne Feld size wird im Konstruktor nicht initialisiert. Dein Pointer-Problem kannst du ganz einfach umgehen, indem du das Feld data direkt als Zeiger auf ein Array vereinbarst:
Delphi-Quellcode:
Gruß Hawkeye
type
// möglicherweise auch bei Delphi3 schon in SysUtils vereinbart... PWordArray = ^TWordArray; TWordArray = array [0..(MaxInt div SizeOf(Word)) - 1] of Word; TDynArray = class private FCapacity : Cardinal; FData : PWordArray; public constructor Create (Capacity: Cardinal); destructor Destroy; override; function GetWord (Index: Cardinal): Word; end; constructor TDynArray.Create (Capacity: Cardinal); begin inherited Create; GetMem (FData, Capacity * SizeOf(Word)); FCapacity := Capacity; end; destructor TDynArray.Destroy; begin FreeMem (FData, FCapacity * SizeOf(Word)); inherited; end; function TDynArray.GetWord (Index: Cardinal): Word; begin Result := FData[Index]; end; |
Re: Pointer/Cardinal-Casterei beenden
Danke für die vielen Antworten,
Zitat:
Delphi-Quellcode:
Klappt nicht, der will einen ordinalen Typen, dh. ich müsste wieder casten.
Inc(var X, N: LongInt);
Zitat:
Zitat:
Ich werde jetzt die "schönere" Array-basierende Lösung anstreben. MfG, Bug |
Re: Pointer/Cardinal-Casterei beenden
Zitat:
|
Re: Pointer/Cardinal-Casterei beenden
Liste der Anhänge anzeigen (Anzahl: 1)
Zitat:
MfG, Bug //EDIT: Ich verwende jetzt die Array-basierende Lösung, ohne Probleme :dp: |
Re: Pointer/Cardinal-Casterei beenden
Versuch mal einen typisierten Zeiger. Bei einem untypisierten Zeiger kann der Compiler nicht wissen, um wie viele Bytes inkrementiert werden soll, was vielleicht zu der Fehlermeldung führt.
|
Re: Pointer/Cardinal-Casterei beenden
Zitat:
![]() Inc(ptr); entspricht Ptr := ptr + sizeof(ptr^); bzw: p += sizeof(*p); |
Alle Zeitangaben in WEZ +1. Es ist jetzt 16:25 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-2025 by Thomas Breitkreuz