gpt4 book ai didi

c++-cli - 从类成员编码托管字符串

转载 作者:行者123 更新时间:2023-12-04 07:18:07 24 4
gpt4 key购买 nike

使用 marshal_cppstd.hmsclr::interop::marshal_as<>我可以将托管字符串编码到 std::string像这样:

String^ managed = "test";
std::string unmanaged = marshal_as<std::string>(managed);

现在当 managed是我正在编写代码的类的成员,在执行以下操作时出现错误:
std::string unmanaged = marshal_as<std::string>(this->managed);

错误说:

no instance of overloaded function "marshal_as" matches the argument list



或者作为编译器错误 C2665:

'msclr::interop::marshal_as': none of the 3 overloads could convert all the argument types



当我更改代码以使用辅助变量时,它可以工作:
String^ localManaged = this->managed;
std::string unmanabed = marshal_as<std::string>(localManaged);

这里一定有一些隐式转换,不是吗?为什么会发生这种情况以及如何使简单的单线工作?

最佳答案

是的,这是一个非常糟糕的错误消息,并不能帮助您发现真正的问题。模板错误消息通常很难理解。它可以使用一些重现代码:

#include "stdafx.h"
#include <string>
#include <msclr\marshal_cppstd.h>

using namespace System;
using namespace msclr::interop;

ref class Example {
String^ managed;
public:
void test() {
auto bad = marshal_as<std::string>(this->managed); // C2665
auto copy = this->managed;
auto good = marshal_as<std::string>(copy);
}
};

您必须在“输出”窗口中查看编译器正在努力尝试找到与参数类型匹配的 marshal_as<> 模板函数版本。您会看到它考虑了两个模板特化,但不是您想要的那个。这是:
template <class _To_Type, class _From_Type>
inline _To_Type marshal_as(const _From_Type&);
_From_Type&参数是麻烦制造者,请注意它是如何非托管引用的, & .与跟踪引用相反, % .或者只是简单的 ^像 System::String 这样的引用类型是理所当然的。

很难看出的是,引用 this->managed 之间存在巨大差异。对比 copy .在像 Example^ 这样的对象中, this指针不稳定。它的值可以在此代码运行时更改,在触发垃圾收集时发生。大多数程序中的可能性不大,但不是零。当程序中的另一个线程从 GC 堆分配并触发收集时发生。那种事情发生〜一年一次。

如果收集恰好在 marshal_as<>() 执行其工作时发生,那将是非常灾难性的。在 GC 压缩堆后,非托管引用变为无效并指向垃圾。 C++/CLI 编译器不能让这种情况发生,所以它不考虑 this->managed&作为 _From_Type& 的有效替代品.甚至从不看它。模板特化也无法匹配,C2665 是必然的结果。

copy 的巨大差异论据是它的地址总是稳定的。以未优化的代码存储在堆栈帧中,通常在优化器完成后存储在 CPU 寄存器中。所以 copy&_From_Type& 的有效替代品并且编译器可以毫不费力地生成模板代码。

因此,您找到的解决方法是完全有效的,并且是执行此操作的最佳方法。如果编译器只是为我们做这件事就好了,但事实并非如此。别名问题也不好,有时您必须将值复制回来。只是关于编写 C++/CLI 代码以及混合托管代码和 native 代码的结果,您必须了解的一些事情,您一定会在某一天再次遇到它。

关于c++-cli - 从类成员编码托管字符串,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41298978/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com