【问题标题】:How to pass UTF-8 string from Delphi to a DLL C extern function?如何将 UTF-8 字符串从 Delphi 传递给 DLL C 外部函数?
【发布时间】:2016-08-30 06:56:24
【问题描述】:

我正在从 Delphi 调用 Visual Studio 编译的 DLL 中的 C extern 函数。 DLL 方法又调用一个 C++ 方法,该方法将 C++ 字符串类型作为参数。 Delphi 端的字符串是 UTF-8 编码的(没有 BOM)。我需要确保采用字符串类型的 C++ 方法获取 UTF-8 编码的字符串。

我可以修改 DLL 源代码。我的问题:

我在 Delphi 端的 UTF-8 字符串是字符串类型。 C extern 方法应该采用什么类型? PChar,PWideChar?以及如何将其转换为 C++ 字符串类型?

注意:我不能先将 UTF-8 字符串转换为 AnsiString,因为编码存储了一些必须保留的希腊字母。 C++ 端将复制 Delphi 字符串并处理任何分配的内存。

Delphi 结束(使用 XE6):

mystr : string;

callCExternMethod (mystr) // cast to what?

C++ 结束(使用 VS 2013):

void callCExternMethod (????? mystr) {

  // convert mystr to C++ string type

  callCPlusPlusMethod (takes C++ string type)
}

【问题讨论】:

标签: c string delphi utf-8


【解决方案1】:

在 Delphi 方面,参数是 PAnsiChar,您可以这样传递:PAnsiChar(Utf8String(str))

在 C++ 端,您收到的参数为 const char*

显然您需要确保调用约定匹配。

【讨论】:

  • 那行得通。我感谢你的回答。知道答案后,我现在可以看到类似的回复,例如stackoverflow.com/questions/21867113/…,由于某种原因没有出现在我的搜索中。我为不必要地占用响应者的时间而道歉。请删除问题是否被认为是多余的。
  • 在 Delphi 2009+ 中,UTF8Encode() 已弃用,请改用 UTF8StringPAnsiChar(UTF8String(str)),或者仅将 str 声明为 UTF8String,然后将其类型转换为 -是:PAnsiChar(str).
  • @RemyLebeau UTF8String 在 LLVM 的“nex gen”Delphi 中被禁止
  • @Arioch'The:UTF8String and RawByteString() have been re-enabled for mobile platforms in Delphi 10.1 Berlin。如果你不想依赖UTF8String,那么你可以改用TEncoding.UTF8.GetBytes()
  • @RemyLebeau 所以他们最终决定停止 pi.. 随风吐痰?我很惊讶:-)
【解决方案2】:

另一种选择是使用UTF8String 类型:

mystr : string;
u8: UTF8String;

u8 := UTF8String(mystr);
callCExternMethod(PAnsiChar(u8));

注意:UTF8String 类型不适用于 Delphi XE5 到 10.0 Seattle 的移动平台,除非您使用补丁来启用它:

http://andy.jgknet.de/blog/2013/10/the-return-of-the-byte-strings/

UTF8String 已从 Delphi 10.1 Berlin 开始重新启用以在移动设备中使用。

【讨论】:

  • 您需要显式类型转换以避免“W1057 Implicit string cast from 'string' to 'UTF8String'”警告:u8 := UTF8String(mystr);
  • 我个人最好禁用该特定警告。在显式类型转换的情况下,虽然不需要临时变量。
  • 我不会禁用警告。 隐式 字符串强制转换可能 修改数据,这就是为什么警告甚至存在的原因。 explicit 类型转换告诉编译器您理解并接受风险。警告发生在将一种字符串类型隐式分配给不同的字符串类型时。如果目标字符串类型是 Ansi 字符串,则会收到稍有不同的警告:W1058 Implicit string cast with potential data loss from 'string' to 'AnsiString'
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2011-05-10
  • 2012-08-08
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2010-12-15
相关资源
最近更新 更多