我喜欢Pascal的清晰度,所以请相信下面的代码片段和问题标题是不言自明的:
procedure TForm1.FormClick(Sender: TObject);
const
N = 42; { fnord }
type
{ this structure merely defines memory layout }
TStringStruct = record
NumberOfCharacters: Cardinal;
{ this array supposed to be friendly for the string type }
StringCompatibleArray: array [0..N-1] of Char;
end;
{ actual work is done with pointer to that structure }
PStringStruct = ^TStringStruct;
var
StringStruct: PStringStruct;
S: string;
begin
StringStruct := PopulatedElsewhere;
{ most pleasant code but will copy no more than N characters }
S := StringStruct^.StringCompatibleArray;
{ this construct works but is way too ugly and complex }
SetString(
S,
{ in particular: must reference the array and then typecast to make it work }
{ default $T- state assumed, unfortunately $T+ has global effect and not useful here }
PChar(@StringStruct^.StringCompatibleArray),
StringStruct^.NumberOfCharacters
);
end;
Run Code Online (Sandbox Code Playgroud)
如果有人想要正式的问题:我想看看我必须执行哪些选项,最好不要比显示的SetString
电话更模糊.
注意:我知道解除引用运算符对于结构化类型是可选的.
SetString
通常是要走的路.如果人们继续对其有用性一无所知,那只是模糊不清.类型转换是必要的,因为有两个重载,并且char数组与预期的参数类型(PAnsiChar和PWideChar)不完全匹配.
它很冗长,但在你的情况下,它很容易包含在你的数据类型的函数中,比如ToString
.正如David在评论中建议的那样,您可以让该函数成为Implicit
运算符,然后自动获得转换:
class operator TStringStruct.Implicit(const Value: TStringStruct): string;
begin
SetString(Result, Value.StringCompatibleArray, Value.NumberOfCharacters);
end;
S := StringStruct^;
Run Code Online (Sandbox Code Playgroud)