我希望我的代码可以保留在遗留C ++(使用“NULL”的C ++代码)和新的C ++ 11标准(使用“nullptr”的C ++代码)上
我正在使用GCC,但是当我完成最重要的事情时,还计划为VS重新编译整个代码库。
我是否应该期待GCC和VS都会做类似
的事情#define NULL nullptr
或者我自己会做得更好(当然使用不同的名称,其中MY_LIB将被我的库后缀替换)?
#ifndef nullptr
#define MY_LIB_NULL NULL
#else
#define MY_LIB_NULL nullptr
#endif
我想要实现的是编译的代码,无论C ++ 11的功能是否已经实现(并且由于我没有使用模板,因此很少有)。
例如关键字“覆盖”和“最终”已经完成。
MY_LIB_OVERRIDE //macro, defines to "override" if c++11 is present.
MY_LIB_FINAL //macro, defines to "final" if c++11 is present.
我问这个问题是因为我知道“nullptr”问题有点奇怪,所以也许只是我已经为覆盖和最终做了同样的事情,这是错误的。需要对此提出意见。任何帮助都很好。
答案 0 :(得分:2)
您可以通过以下方式创建my_nullptr
类型的“false”my_nullptr_t
:
const class my_nullptr_t
{
public:
/* Return 0 for any class pointer */
template<typename T>
operator T*() const
{
return 0;
}
/* Return 0 for any member pointer */
template<typename T, typename U>
operator T U::*() const
{
return 0;
}
/* Safe boolean conversion */
operator void*() const
{
return 0;
}
private:
/* Not allowed to get the address */
void operator&() const;
} my_nullptr = {};
这适用于C ++ 03和C ++ 11,并且应始终是安全的,无论哪种C ++ 11功能都实现。该解决方案实际上已经在this topic中讨论过,它基于the Official proposal提出了nullptr_t
版本。
答案 1 :(得分:1)
NULL
是一个扩展为空指针常量的宏。它仍然像以前一样工作。必须与非C ++ 11编译器一起使用的代码应使用NULL
。
答案 2 :(得分:0)
我认为以下方法有效:
#include <cstddef>
#ifndef MY_LIB_NULL
#ifndef NULL //check for NULL
#define MY_LIB_NULL nullptr
#else
#define MY_LIB_NULL NULL ///use NULL if present
#endif
#endif
基本上我检查“NULL”。这是一个宏,可以检查,直到编译器附带该宏(可能是),而不是使用宏有效,当编译器只提供“nullptr”而不再有NULL时,则使用nullptr(可能在遥远的未来,但似乎我们可以愉快地继续使用NULL!)
我认为这比重新定义“nullptr”更安全(就像大多数人想做的那样)