我有一个标有C ++ 17的[[nodiscard]]
属性的结构。定义如下:
struct [[nodiscard]] MyObject final
{
explicit MyObject(int id);
~MyObject();
MyObject(const MyObject&) = delete;
MyObject& operator=(const MyObject&) = delete;
int id;
};
现在,我想从动态库中导出它。
在MSVC上,语法
struct __declspec(dllexport) [[nodiscard]] MyObject final
可以正常工作。但是GCC无法同时编译
struct __attribute__((dllexport)) [[nodiscard]] MyObject final
和struct [[nodiscard]] __attribute__((dllexport)) MyObject final
:编译器无法处理这种语法。语法
__attribute__((dllexport)) struct [[nodiscard]] MyObject final
可以编译,但似乎没有执行我想要的操作,因为它会产生以下警告::1:49:警告:'struct声明中忽略了属性
MyObject'[-Wattributes]
1 | __attribute__((dllexport)) struct [[nodiscard]] MyObject final
| ^~~~~~~~
:1:49:注意:“ struct MyObject”的属性必须遵循
'struct'关键字
那么,如何从GCC上的动态库导出
[[nodiscard]]
结构? 最佳答案
所有这些都适用于dllexport
和dllimport
。
这似乎是GCC解析器中的错误。
使用manages to parse和struct __attribute__((dllexport)) [[nodiscard]] MyObject ...
版本。
如@Artyer所述,GCC(和Clang)支持dllexport
-[[gnu::dllexport]]
的C ++语法。
还要注意的是,Windows上的GCC(MinGW)支持__declspec(dllexport)
与Visual C ++兼容,并且实际上可以正确解析class __declspec(dllexport) [[nodiscard]] Test ...
(已通过GCC 8.1.0测试)。
以上所有条件均假定您正在针对Windows进行编译,其中dllexport
实际上表示某些含义。在其他平台上,编译器只会忽略它(通常会发出警告)。
在Linux上,应该使用-fvisibility=hidden
隐藏除属性visibility("default")
选择的符号以外的所有符号。没有“导入”替代方法-在构建和使用库时均使用"default"
。在Linux上导出类时,不需要的任何内容都可以用visibility("hidden")
标记以覆盖该类的属性。
GCC和Clang支持visibility
的两种语法:__attribute__((visibility("default")))
和[[gnu::visibility("default")]]
。
可以在HERE中找到有关GCC可见性的更多信息。
我不确定从共享库中导出符号在MacOS上如何工作(也许与Linux上的相同?)。
关于c++ - gcc-如何在结构定义中组合__attribute __((dllexport))和[[nodiscard]]?,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/57993818/