c++ 库的公共头文件中应该包含哪些内容?
Posted
技术标签:
【中文标题】c++ 库的公共头文件中应该包含哪些内容?【英文标题】:What should be included in the public header files of a c++ library? 【发布时间】:2018-11-04 18:02:50 【问题描述】:我正在构建一个小型 c++ 共享库,它有一个像这样的类(在头文件上)
class Foo
...
std::optional<some_type> _bar;
...
;
由于std::optional
是C++17,任何包含上述文件的人都需要编译C++17。但是,_bar
不是库的公共接口的一部分。 _bar
仅在实现中使用。所以,我的问题是,我怎样才能公开一个只公开公共方法但维护我的实现 C++17 的头文件?我希望我不需要强迫图书馆的用户使用 C++17,对吧?
我也在使用 CMake 来生成构建文件,如果这很重要的话。
【问题讨论】:
由于 C++ 没有指定 ABI,您的客户可能需要使用完全相同的编译器。 PIMPL 是您正在寻找的习语 :) 但是您的库必须使用与用户代码相同的编译器进行编译,所以这有点争议——除非您从 C++ 接口转发所有内容通过稳定的 C ABI 到 C++ 中的底层静态链接 C++ 运行时实现,然后可以使用不同的编译器进行编译。唯一与 C++-ABI 兼容的编译器对,其中一个是 C++17,另一个不是,是 VC++2015 和 2017。对于任何其他编译器组合,您必须使用稳定的 C ABI .不过,您也可以拥有一个仅包含标头的库! 您也可以链接到 C++ API,但它必须是可靠的(即确保在一个库中分配的任何内容在 Windows 上的该库中被释放,而在 Linux 上,您需要发布最高如果您使用的是 libstdc++ 版本)。 【参考方案1】:由于您正在构建共享库:
您可以定义一个基类BaseFoo
与所有接口(纯虚拟)。
然后从BaseFoo
派生你的Foo
,并添加一个工厂函数:getFoo
之后,将您的Foo
实现为动态库,并导出工厂函数(__attribute__ ((visibility ("default")))
)
现在,将 BaseFoo
标头与动态库一起发送(确保客户端使用相同版本的 libstdc++)。
【讨论】:
以上是关于c++ 库的公共头文件中应该包含哪些内容?的主要内容,如果未能解决你的问题,请参考以下文章