我可以在用于C ++ 11客户端应用程序的库中使用C ++ 14吗?

时间:2015-09-25 17:03:41

标签: c++ c++11 c++14

如果我正在建立一个图书馆,我假设某些"客户"该库可能只使用C ++ 11,我可以使用C ++ 14为其内部编译库本身吗?与C ++ 11相比,是否存在API / ABI /链接兼容性问题?只要我避免使用公共API中的某些新功能,使用C ++ 14实现和构建库是否安全?如果是这样,我必须避免哪些内容?或者在最终的软件项目中混合使用C ++ 11和C ++ 14本质上是不兼容的?

它是一个跨平台的库,BTW,所以我需要在Linux,OSX和Windows上构建它。

1 个答案:

答案 0 :(得分:9)

  

如果我正在构建一个库,我假设该库的某些“客户”可能只使用C ++ 11,那么我可以使用C ++ 14为其内部编译库本身吗?

是的,总的来说应该是可能的。

我正是为GCC实现的Filesystem TS而做的。 <experimental/filesystem>标头用纯C ++ 11编写,可以包含在C ++ 11客户端中,但libstdc++fs.a中的实现是用C ++ 14编写的。

  

与C ++ 11相比,是否存在API / ABI /链接兼容性问题?

C ++ 11和C ++ 14之间没有任何变化,需要实现来破坏它们的链接时间兼容性。这并不意味着实现不会打破它,但它们不是必需的。

对于GCC,我相信C ++ 11和C ++ 14完全兼容API和ABI,除了下面提到的constexpr和大小 - 释放问题。

  

使用C ++ 14实现和构建库是否安全,只要我避免使用公共API中的某些新功能,如果是这样,我必须避免哪些内容?

这取决于你的编译器,但理论上它是可能的。

显然避免在C ++ 11中无效的任何C ++ 14语言特性(例如函数返回类型推导,或具有auto参数的通用lambda,或变量模板)和任何C ++ 14个库实体,如std::make_uniquestd::integer_sequence, or std :: shared_timed_mutex`。

可以在SD-6中找到C ++ 14中几乎所有更改的列表。

需要注意的一点是,在C ++ 11和C ++ 14之间,非静态constexpr成员函数的含义发生了变化。在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的那个版本。