27

我正在将我的应用程序转换为 Delphi 2009,并遇到了一些需要将字符串(宽)转换为 AnsiString 的调用的有趣问题。

这是一个示例来演示我遇到的问题:

var
  s: PAnsiChar;

...

s := PAnsiChar(Application.ExeName);

对于 Delphi 2007 和以前的版本, s := PChar(Application.ExeName) 将返回应用程序 exe 路径。

使用 Delphi 2009,s := PAnsiChar(Application.ExeName) 仅返回“E”。

我的猜测是因为我正在将 unicode 字符串转换为 ansi 字符串,但我如何转换它以便 PAnsiChar 获得完整的字符串?

4

6 回答 6

40

我这里没有Delphi 2009,所以无法查看。但也许你必须尝试:

s := PAnsiChar(AnsiString(Application.ExeName));

正如 gabr 已经指出的那样,这不是一个很好的做法,只有在 100% 确定时才会使用它。该字符串仅包含直接映射到 ANSI 范围的字符。

这就是您应该收到警告的原因,因为您正在将 Unicode 转换为 ANSI。

于 2008-11-12T12:19:27.030 回答
5

而不是使用 type String,使用RawByteString

s: RawByteString;

s := LoadSomeRegularString(usually a string type);

PAnsiChar(s) <<< all fine.
于 2010-02-25T20:20:16.743 回答
1

Gamecat 显式转换有效。我在下面更详细地解释了这个问题,以便有人可以指出更好的解决方案。

我正在使用以下函数来检索应用程序编译日期:

function LinkerTimeStamp(const FileName: string): TDateTime;
var
  LI: TLoadedImage;
begin
  {$IFDEF UNICODE}
  Win32Check(MapAndLoad(PAnsiChar(AnsiString(FileName)), nil, @LI, False, True));
  {$ELSE}
  Win32Check(MapAndLoad(PChar(FileName), nil, @LI, False, True));
  {$ENDIF}
  Result := LI.FileHeader.FileHeader.TimeDateStamp / SecsPerDay + UnixDateDelta;
  UnMapAndLoad(@LI);
end;

MapAndLoad 需要一个 PAnsiChar 作为 ImageName 参数,所以我需要转换 unicode 字符串。是否有任何其他替代方法可以先显式转换为 AnsiString?

于 2008-11-12T13:10:00.190 回答
0

WideCharToMultiByte可以帮助你。

于 2008-11-12T12:37:12.500 回答
0

我有同样的问题。PAnsiChar唯一指向第一个字符。我编写了以下函数来处理旧功能。

// This function converts a string to a PAnsiChar
// If the output is not the same, an exception is raised
// Author: nogabel@hotmail.com

function StringToPAnsiChar(stringVar : string) : PAnsiChar;
Var
  AnsString : AnsiString;
  InternalError : Boolean;
begin
  InternalError := false;
  Result := '';
  try
    if stringVar <> '' Then
    begin
       AnsString := AnsiString(StringVar);
       Result := PAnsiChar(PAnsiString(AnsString));
    end;
  Except
    InternalError := true;
  end;
  if InternalError or (String(Result) <> stringVar) then
  begin
    Raise Exception.Create('Conversion from string to PAnsiChar failed!');
  end;
end;
于 2009-03-05T13:20:21.053 回答
-2

我觉得你有点过分了。每个 Win32 API 函数都有一个对应的 unicode,如果它需要一个字符串的话。尝试MapAndLoadW而不是MapAndLoad ...

于 2009-04-20T11:34:44.930 回答