System::String 到 QString

Posted

技术标签:

【中文标题】System::String 到 QString【英文标题】:System::String to QString 【发布时间】:2011-04-13 19:26:54 【问题描述】:

我正在调用一个 c++ 库,并且正在围绕该库编写一个托管 C++ 包装类。这些方法采用 QString 的参数,有时还引用 QString 以便可以填写值。我尝试使用 std::string 并且在我编译它并将其链接到 c# 之前它似乎很好,就像方法声明一样不存在。所以现在我试图传入 System::String 但我不知道如何将其转换为 QString。所以这个问题的答案可以有两种形式之一。 1. 为什么我不能将 c# 中的方法引用到具有 std::string 参数的托管 c++ 代码?或者,如何将 System::String 转换为 QString?

【问题讨论】:

你用的是什么版本的VC++? 我正在使用 Visual Studio 2005 【参考方案1】:

为什么我不能将 c# 中的方法引用到具有 std::string 参数的托管 c++ 代码?

只有 POD 类型可以在本机代码和托管代码之间来回自动封送。 std::string 不是 POD 类型。

或者,如何将 System::String 转换为 QString?

#include <string>
#include <QString>
#include <msclr/marshal_cppstd.h>

QString SystemStringToQString(System::String^ str)

    using namespace msclr::interop;
    return QString::fromStdWString(marshal_as<std::wstring>(str));

编辑(回应 cmets 的回答 #6205169):

建议的内存泄漏修复:

std::wstring MarshalString(String^ s)

    using namespace System::Runtime::InteropServices;
    std::wstring ret;
    IntPtr p = Marshal::StringToHGlobalUni(s);
    if (p.ToPointer())
    
        ret.assign((wchar_t const*)p.ToPointer());
        Marshal::FreeHGlobal(p);
    
    return ret;

就性能而言,它的效率远低于它可能的水平,但它应该可以工作并且不应该泄漏。

【讨论】:

'msclr' : 不是类或命名空间名称 @dko :那你要么是 VC++ 版本太旧,要么没有#include &lt;msclr/marshal_cppstd.h&gt;。您使用的是哪个版本的 VC++? @dko :作为健全性检查,您正在从 C++/CLI 尝试此操作,而不是 C# 或 C++,对吗? @ildjarn 我正在从 Visual Studio 2005 的 C++/CLI 尝试这个 我认为问题在于我正在使用的库中内置的 Qt 库已经过时了。【参考方案2】:

看这个:

http://www.codeguru.com/forum/showthread.php?t=372298

它应该让您使用char*,它可以轻松转换为QString

【讨论】:

那些不起作用,即使使用正确的包含,编译器也找不到 PtrToStringChars 或 Marshal。【参考方案3】:

好吧,我已经成功了一半。我只需要知道这些方法是否会造成内存泄漏以及我能做些什么

我创建了一些辅助方法来执行此操作。我需要这样做才能从旧的 Qt 库迁移到 CLI String。我无法更新 Qt 库,因为我无法控制那部分代码。

void MarshalString (  String ^ s, wstring& os ) 
    using namespace Runtime::InteropServices;
    const wchar_t* char = 
        (const wchar_t*)(Marshal::StringToHGlobalUni(s)).ToPointer();
    os = char;

QString SystemStringToQt( System::String^ str)

    wstring t;
    MarshalString(str, t);
    QString r = QString::fromUcs2((const ushort*)t.c_str());
    return r;

String ^ QtToSystemString( QString * str)


    wchar_t * wcar = (wchar_t *)str->ucs2();
    String^ r = gcnew String(wcar);
    return r;

【讨论】:

是的,这些肯定会造成内存泄漏。要修复泄漏,请将Marshal::FreeHGlobal(IntPtr(char)); 放在os = char; 之后。 @ildjarn 错误 3 错误 C2440: '' : 无法从 'const wchar_t *' 转换为 'System::IntPtr' 啊,对,是const。我将使用我提出的修复来编辑我的答案,因为在评论中传递比单个表达式更长的代码是很痛苦的。 :-P @ildjarn 抱歉,我删除了我的评论,因为我自己修复了它。感谢您的帮助。

以上是关于System::String 到 QString的主要内容,如果未能解决你的问题,请参考以下文章

如何将 LanguagePrimitives.GenericZero / get_Zero 添加到 System.String?

jQuery AJAX POST 到 ASMX Web 服务导致“无法将 System.String 类型的对象转换为 System.Collections.Generic.IDictionary”

无法创建“System.String”类型的实例

无法在 DataReader.GetString() 中将“System.Int32”类型的对象转换为“System.String”类型

将 CString 数组转换为 System::String

找不到方法:“Void System.Web.UI.HtmlControls.HtmlForm.set_Action(System.String)”