PDA

View Full Version : The dereference operator is weird



chronozphere
11-11-2010, 07:12 PM
Hey delphi users,

I just discovered something odd. Check this out:



type
PPPPMyRec = ^PPPMyRec;
PPPMyRec = ^PPMyRec;
PPMyRec = ^PMyRec;
PMyRec = ^TMyRec;
TMyRec = record
Str: String;
Int: Integer;
end;

procedure TForm1.Button5Click(Sender: TObject);
var
P: PMyRec;
PP: PPMyRec;
PPP: PPPMyRec;
PPPP: PPPPMyRec;
begin
New(P);
P^.Str := 'test';
P^.Int := 5;

PP := @P;
PPP := @PP;
PPPP := @PPP;

//A pointer to a record... only one dereference needed
ShowMessage(P^.Str);

//A pointer to a pointer to a record... STILL ONLY ONE DEREFERENCE NEEDED!!
ShowMessage(PP^.Str);

//triple pointer... now we need to add an extra dereference operator
ShowMessage((PPP^)^.Str);

//Yet another extra ^
ShowMessage(((PPPP^)^)^.Str);

Dispose(P);
end;


I think this is disturbing. In the second case, it's not possible to set the value of P by using PP^, because it dereferences 2 times at once. :o Is there a way to do that?

I hope fpc is more consistent with these things.

JSoftware
11-11-2010, 07:24 PM
In Delphi it'll try to automatically dereference if you don't do it

Eg. this would work. It wouldn't work in FPC, unless you use mode Delphi


New(P);
P.Str := 'test';
P.Int := 5;

chronozphere
11-11-2010, 10:44 PM
Thanks for your response. :)

Is it actually possible that PPPMyRec is automaticly dereferenced or does it only do second-degree pointers?

Delphi is a great IDE, but "automation" like this actually suck pretty badly. It makes things non-intuitive. :(

mleyen
12-01-2011, 10:30 AM
I think this is disturbing. In the second case, it's not possible to set the value of P by using PP^, because it dereferences 2 times at once. :o Is there a way to do that?

Cast the typed Pointer to a Pointer and evrything is wonderful. ;D

var
P: PMyRec;
AnotherP: PMyRec;
PP: PPMyRec;
// PPP: PPPMyRec;
// PPPP: PPPPMyRec;
begin
New(P);
P^.Str := 'test';
P^.Int := 5;
New(AnotherP);
AnotherP.Str := 'AnotherTest';
AnotherP.Int := 6;

PP := @P;
// PPP := @PP;
// PPPP := @PPP;

ShowMessage(P.Str);
Dispose(P);
Pointer(PP^) := AnotherP;
ShowMessage(P.Str);

Dispose(AnotherP);
end;




Is it actually possible that PPPMyRec is automaticly dereferenced or does it only do second-degree pointers?
i dunno, but normaly i always notice if something is going wrong.