1

我在 C++ CLI 中有下一堂课:

   public ref class MyClass
   {
        public:
           MyClass(void);
           virtual bool Init();

           cliext::vector<int>^ ListOfNumbers();
   };

我想从公共功能中接收 int 向量。

这是实现:

cliext::vector<int>^ MyClass::ListOfNumbers()
{
    cliext::vector<int>^ devs = gcnew cliext::vector<int>();
    devs->push_back(1);
    return devs;
}

我的问题是我收到下一个警告:

警告 C4677:“ListOfNumbers”:非私有成员的签名包含程序集私有类型“cliext::vector<_Value_t>”

有人可以告诉我原因吗?我可以从公共函数 C++ CLI 类接收项目集合吗?

4

3 回答 3

3

实际上,我不知道,但如果所有 CLI模板实例化都是私有的并且不能通过公共程序集接口公开,我不会感到惊讶。您知道,由 C++/CLI 生成的模板类型在与其他 .Net 程序集对话时并没有真正的帮助,而“与其他 .Net 对话”正是 C++/CLI 的用途。

“本机 C++ 模板”(我可以这样称呼它们)只能从 C++ 端使用和访问。CLR 运行时通常无法对它们进行操作,因为编译器的 C++ 部分无法为它们生成正确的类型描述。(*)

要创建 .Net 接口,请使用 .Net BCL 类型。使用泛型而不是模板。所以,看看像System.Collections.Generic.List<>. 它们可以安全地暴露在公共接口中。(**)

请记住,C++/CLI 是原生 C++ 和 .Net的混合体。您可以轻松访问这两个世界,但这些世界并不真正喜欢混合;)

编辑:(*)正如 JochenKalmbach 提醒的那样,它适用于“本机”模板。微软已经准备了一个特殊的 STL 版本,它实现了一些核心集合接口,因此它vector实际上实现了System.Collection.Generic.IEnumerable. 那vector这里还是受原生限制,不能直接通过汇编接口作为本身(as vector<>)发布。但是,后一种类型(IEnumerable)是完全正常的 CLR 类型,可以暴露。因此,尝试例如:

System::Collections:::Generic::ICollection<int>^ MyClass::ListOfNumbers()
{
    cliext::vector<int>^ devs = gcnew cliext::vector<int>();
    devs->push_back(1);
    return devs;
}

它可能会编译 - 但我没有检查过。

于 2014-02-10T10:21:09.310 回答
2

cliext::vector 不打算跨程序集边界使用。它只能在您的 C++/CLI 项目中使用。所以添加一个“private:”并在公共接口中返回一个“IEnumerable”。

于 2014-02-10T10:21:21.837 回答
0

是的,您可以退货。检查这个链接

http://msdn.microsoft.com/en-us/library/bb385659.aspx

尽管如果您想在 .NET 框架或 Native C++ 中使用此方法,您必须将此集合转换为该特定语言的兼容集合。

于 2014-02-10T10:20:43.340 回答