如何将空字符串解析为字节数组?

How to parse empty string to array of byte?

我必须使用一个旧单元,该单元在 Android 上使用 ansistring、ansichar 等,之前构建于 Delphi 2007,因此我正在努力使其与 XE7 兼容。

我遇到过几行将空字符串放入 AnsiString 的行,如下所示:FAnsiString := '',但现在 AnsiString 是一个字节数组 (FAnsiString : array of Byte) 我明白了消息 E2010 类型不兼容。

我尝试通过为数组创建一个类型 (type TArrayOfByte = array of Byte) 来解析它,并尝试像这样解析它:FAnsiString := TArrayOfByte ('')。 但后来我得到 E2089 Invalid TypeCast.

如何让它正常工作?

下面对其工作原理进行了简化。 基本上我想要一个 returns 字节数组的函数。 根据参数,该函数的结果应该是一个空字符串。

{$ifdef android}
  type AnsiString = array of Byte;
{$endif}

function FooBar(arguments) : AnsiString
begin
  if false then
  Result := '';
end;

Delphi 字符串和动态数组在为空时都包含一个 nil 指针。所以这个:

var
  FAnsiString: AnsiString;

FAnsiString := '';

在幕后有效地执行此操作:

// FAnsiString := '';
if Pointer(FAnsiString) <> nil then
begin
  // decrement reference count, if 0 then free memory ...
  Pointer(FAnsiString) := nil;
end;

动态数组做完全相同的事情。这个:

var
  FAnsiString: array of Byte;

FAnsiString := nil;
// Alternatively:
// SetLength(FAnsiString, 0);

实际上在做与幕后 AnsiString 清理相同的事情:

// FAnsiString := nil;
if Pointer(FAnsiString) <> nil then
begin
  // decrement reference count, if 0 then free memory ...
  Pointer(FAnsiString) := nil;
end;

AnsiString 和动态数组都是编译器管理的引用计数类型。它们都自动初始化为 nil.

同样,AnsiString 比较空字符串:

var
  FAnsiString: AnsiString;

if FAnsiString = '' then
...
if FAnsiString <> '' then

实际上只是在检查 nil 指针:

if Pointer(FAnsiString) = nil then
...
if Pointer(FAnsiString) <> nil then

与动态数组相同,只有你可以在没有类型转换的情况下做到这一点:

var
  FAnsiString: array of byte;

if FAnsiString = nil then
...
if FAnsiString <> nil then

另一种方法是使用 Length()SetLength(),它适用于字符串和动态数组:

var
  FAnsiString: AnsiString;

if Length(FAnsiString) = 0 then
  ...

if Length(FAnsiString) <> 0 then
  ...

SetLength(FAnsiString, 0);

var
  FAnsiString: array of byte;

if Length(FAnsiString) = 0 then
  ...

if Length(FAnsiString) <> 0 then
  ...

SetLength(FAnsiString, 0);

当然,还有 Andreas Hausladen 的补丁可以在移动编译器中启用 AnsiString

The Return of the Byte-Strings

System.ByteStrings support for XE5 Update 2(以及 XE6 和 XE7)