如果我正在构建一个库,我假设该库的某些“客户端”可能只使用 C++11,那么我可以使用 C++14 来编译该库本身吗?与 C++11 相比是否存在 API/ABI/链接兼容性问题?只要避免公共(public) API 中的某些新功能,使用 C++14 实现和构建库是否安全?如果是这样,我必须避免什么?或者在最终软件项目中混合使用 C++11 和 C++14 本质上是不兼容的?
顺便说一句,这是一个跨平台库,所以我需要在 Linux、OSX 和 Windows 上构建它。
最佳答案
If I'm building a library where I assume that some "clients" of the library may only be using C++11, can I compile the library itself using C++14 for its internals?
是的,一般来说这应该是可能的。
我正是为 GCC 的文件系统 TS 实现做的。 <experimental/filesystem>
header 是用纯 C++11 编写的,可以被 C++11 客户端包含,但是 libstdc++fs.a
中的实现是用 C++14 编写的。
Are there API/ABI/link compatibility issues versus C++11?
C++11 和 C++14 之间没有变化需要实现来破坏它们的链接时兼容性。这并不意味着实现不会破坏它,但它们不是必需的。
对于 GCC,我相信 C++11 和 C++14 完全兼容 API 和 ABI,除了 constexpr
以及下面提到的大小释放问题。
Is it safe to implement and build the library with C++14 as long as I avoid certain new features in the public API, and if so, what must I avoid?
这取决于您的编译器,但理论上这是可能的。
显然要避免在 C++11 中无效的任何 C++14 语言特性(例如函数返回类型推导,或带有 auto
参数的通用 lambda,或变量模板)和任何 C++14 库实体,例如 std::make_unique
, std::integer_sequence, or
std::shared_timed_mutex`。
可以在 SD-6 中找到 C++14 中几乎所有更改的列表。 .
需要注意的一件事是非静态 constexpr
的含义成员函数在 C++11 和 C++14 之间发生了变化。在 C++11 中,这个成员函数是 const
:
struct X {
constexpr int foo();
};
在 C++14 中它是非常量。为了与 C++11 和 C++14 兼容,您应该明确地将其限定为 const
:
struct X {
constexpr int foo() const;
};
这在 C++11 和 C++14 中意味着同样的事情。
另一个警告是,在 C++11 和 C++14 中,此运算符的含义有所不同:
void operator delete(void*, std::size_t);
如果 C++11 客户端代码定义了该函数,那么用 C++14 编译的库可能最终调用它而不是通常的 operator delete(void*)
那可能会做错事。这可能非常不常见,在实际代码中不是问题,但这是可能的。 G++ 和 Clang 允许您使用 -fno-sized-deallocation
编译 C++14 代码禁用新功能,以便您的 C++14 库代码永远不会调用该版本的 operator delete
.
关于c++ - 我可以在用于 C++11 客户端应用程序的库中使用 C++14 吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/32787244/