从DLL导出STL类 - 为什么返回类型没有警告? [英] Exporting STL class from DLL - why is there no warning from the return type?

查看:358
本文介绍了从DLL导出STL类 - 为什么返回类型没有警告?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我的问题是关于导出一个C ++类与STL里面。例如:

My question is related to exporting a C++ class with STL inside. For example:

class __declspec(dllexport) Hello
{
    std::string   name;

public:
    std::string&  getName();
    void          setName(const std::string& name);
}

各种文章似乎表明这是非常糟糕,这是可以理解的。一切都必须用相同的编译器设置和CRT版本编译。

Various articles seems to indicate that this is very bad, which is quite understandable. Everything must be compiled with the same compiler settings and CRT version. Otherwise everything will crash and burn.

我不明白的是为什么只有数据成员似乎有一个问题。使用下面的代码,我得到: C4251:需要
具有类
的客户端使用的dll接口;这显然是通过导出实例化的std :: string固定的:

What I don't understand is why only data members seem to have an issue. With the below code, I get: "C4251: needs to have dll-interface to be used by clients of class"; which is apparently fixed by exporting the instantiated std::string:

struct __declspec(dllexport) SomeClass
{
    // Removes the warning?
    // http://www.unknownroad.com/rtfm/VisualStudio/warningC4251.html
    //   template class __declspec(dllexport) std::string;

    std::string name;  // Compiler balks at this
}

固定版本是:

// Export the instantiations of allocator and basic_string
template class __declspec(dllexport) std::allocator<char>;
template class __declspec(dllexport) std::basic_string<char, std::char_traits<char>, std::allocator<char> >;

struct __declspec(dllexport) SomeClass
{
    std::string name;  // No more balking!
}

(这将使LNK2005basic_string已定义 DLL,意思是你不能链接到客户端上的CRT - 所以它最终使用DLL中的实例化)。

(This will give LNK2005 "basic_string already defined" when you try to use the DLL, meaning you have to not link in the CRT on the client - so it ends up using the instantiation in the DLL).

返回类型和参数似乎没有

Return types and arguments seem to have no problem with the STL, and do not receive the same treatment data members get from the compiler.

// No exporting required?
struct __declspec(dllexport) SomeOtherClass
{
    std::string  doSomething1();                       // No problemo
    void         doSomething2(const std::string& s);   // No problemo
}



其他信息(问题在上面)



在这两者中:

Additional Info (Question is above)

In both:

class A {
    std::string foo() { return std::string(); }
    // std::string& foo(); gives the same result!
    // std::string* foo(); also gives the same result!
}

class B {
    std::string a;
}

似乎不会导出std :: basic_string或std :: allocator。但是,它们只导出类的成员/函数。

Neither seem to export std::basic_string or std::allocator. Rather, they only export the members/functions of the class.

但是问题中提到的 fixed 版本导出basic_string和allocator。 / p>

However the fixed version mentioned in the question exports both basic_string and allocator.

推荐答案


各种文章似乎表明这是非常糟糕 p>

Various articles seems to indicate that this is very bad

是的,可以。你的项目设置将让你陷入他们警告的那种麻烦。通过值暴露C ++对象需要DLL的客户端使用相同的CRT,以便在DLL中创建的对象可以被客户端应用程序安全地销毁。反之亦然。这要求这些模块使用相同的堆。

Yes, it can be. And your project settings are going to get you into the kind of trouble they are warning about. Exposing C++ objects by value requires the client of your DLL to use the same CRT so that objects that are created in the DLL can be safely destroyed by the client app. And the other way around. Which requires that these modules use the same heap.

并且您的项目设置防止是可能的,编译器警告的要点。您必须指定共享版本的CRT,以便所有模块加载CRT的一次性和唯一实现。

And your project settings prevent that from being possible, the gist of the compiler warning. You must specify the shared version of the CRT so that all modules load the one-and-only implementation of the CRT.

使用Project + Properties,C / C ++ ,代码生成,运行时库设置。你现在有/ MT,它必须是/ MD。对所有模块和所有配置更改此设置。

Fix that with Project + Properties, C/C++, Code Generation, Runtime library setting. You have it now at /MT, it must be /MD. Change this for all modules and all configurations.

这篇关于从DLL导出STL类 - 为什么返回类型没有警告?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆