对于我目前正在开发的代码,我们有时需要使用旧的编译器编译一些旧的系统(例如,我们在旧的IBM BlueGene / L上运行模拟器,谁的支持合同规定了一些相当老的C编译器).代码本身使用shared_ptrs,最初写入使用std :: tr1 :: shared_ptr.当在旧的BlueGene机器上编译时,我很快意识到它没有一个tr1 ::实现,所以我切换到boost :: shared_ptr.结果还有一个boost :: tr1 :: shared_ptr.现在,代码在我们的研究组之外被广泛使用,可携带性变得越来越重要.
在大规模代码库中处理这些不断发展的标准库问题的最佳做法是什么?我假设在新的C11标准中,shared_ptr将不再位于tr1命名空间中,这增加了另一个潜力:std :: shared_ptr,但是我猜测广泛支持这将是一种方法.如果可能,我想使用最新的标准,但需要维护可移植性.我应该坚持提高吗?
解决方法
要检测shared_ptr的命名空间,您需要像autoconf这样的命名空间,这就是为什么autoconf被创建(检测平台/编译器变体)的原因.你可以这样做:
AC_LANG(C++) AC_MSG_CHECKING([for std::shared_ptr]) AC_COMPILE_IFELSE([AC_LANG_PROGRAM( [[#include <memory>]] [[std::shared_ptr<int> have_shared_ptr;]]) ],[ AC_MSG_RESULT([yes]) AC_DEFINE_UNQUOTED([HAVE_STD_SHARED_PTR],1,[Define to 1 if you have the `std::shared_ptr' class.]) ],[ AC_MSG_RESULT([no]) AC_DEFINE_UNQUOTED([HAVE_STD_SHARED_PTR],[Define to 1 if you have the `std::shared_ptr' class.]) ])
重复std :: tr1 :: shared_ptr,boost :: tr1 :: shared_ptr和boost :: shared_ptr.
然后,您可以创建一个shared_ptr.hpp文件,如:
#include <config.h> #if defined(HAVE_STD_SHARED_PTR) namespace ptr = std; #elif defined(HAVE_STD_TR1_SHARED_PTR) namespace ptr = std::tr1; #elif defined(HAVE_BOOST_SHARED_PTR) namespace ptr = boost; #elif defined(HAVE_BOOST_TR1_SHARED_PTR) namespace ptr = boost::tr1; #else # error No shared_ptr found. #endif
你可以使用它作为:
ptr::shared_ptr<int> pointer(new int(5));