Genaugenommen wird mir
SetLength(S, 1) ein Array mit der Länge 2 erstellt, da dem String aus Kompatibilitätsgründen zu PChar noch eine #0 anhängt wird.
Und das bei LongStrings (AnsiString, WideString) ebenfalls mit der Zählung bei 1 beginnen, obwohl es das Längenbyte nicht mehr gibt, sollte ebenfalls allen bekannt sein - ist ja wegen der Kompatitär zu den "alten" ShortStrings.
Hier nochmal die genauen Definitionen der Stringtypen:
Delphi-Quellcode:
Type TShortStringInfo = packed Record
Length: Byte; <<< @VarOfThisType
Chars: packed Array[1..Length(thisString)] of Char;
End;
TDynArrayInfo = packed Record
//MemoryInfo: LongInt;
RefCount: LongInt;
ElementCount: LongInt;
Data: packed Array[0..High(thisArray)] of {ArrayTyp}; <<< @VarOfThisType
End;
TAnsiStringInfo = packed Record
//MemoryInfo: LongInt;
RefCount: LongInt;
ElementCount: LongInt;
Data: packed Array[1..Length(thisString)] of AnsiChar; <<< @VarOfThisType
StringEnd: AnsiChar; < ist immer #0
End;
Code:
@ShortString = TShortStringInfo/TShortStringInfo.Length
@DynArray = TDynArrayInfo.Data/TDynArrayInfo.Data[0]
@String/@AnsiString = TAnsiStringInfo.Data/TAnsiStringInfo.Data[1]
.MemoryInfo gehört eigentlich zum MemoryManager, aber da für jedes Array ein eigener Speicherblock reservert wird, ist das halt "immer" an dieser Stelle