如果未在c ++

时间:2016-09-03 12:35:42

标签: c++ function c++11 methods precompile

我还没有使用C ++ 11,所以我自己编写了函数to_string(whatever)。只有在它们不存在时才应编译它们。如果我切换到C ++ 11,应该跳过它们。我有这样的事情:

#ifndef to_string

string to_string(int a){
    string ret;
    stringstream b;
    b << a;
    b >> ret;
    return ret;
}

string to_string(double a){
    string ret;
    stringstream b;
    b << a;
    b >> ret;
    return ret;
}

#endif

这显然不起作用。这样的事情是可能的,如果是的话,怎么样?

5 个答案:

答案 0 :(得分:14)

这是namespace存在的主要目的之一。

我的建议是将您的个人功能包含在适当的命名空间中,例如:

namespace myns {
  std::string to_string(...) {
    // ...
  }
  // etc...
}

这是避免未来冲突问题的基础。

之后,当您打算使用该功能时,您可以通过MACRO替换简单地选择正确的功能。

类似的东西:

#if (__cplusplus >= 201103L) 
  #define my_tostring(X) std::to_string(X)
#else
  #define my_tostring(X) myns::to_string(X)
#endif

注意__cplusplus pre-defined macro ,其中包含有关标准版本的编译信息。

修改
不那么“暴力”的东西,它将根据标准版本为该特定功能选择合适的命名空间:

#if (__cplusplus >= 201103L) 
  using std::to_string;
#else
  using myns::to_string;
#endif

// ... somewhere
to_string(/*...*/);  // it should use the proper namespace

答案 1 :(得分:9)

您无法测试它们是否已定义,但您可以检查语言版本:

#if __cplusplus < 201103L

(有一组有用的预定义编译器宏here。)

答案 2 :(得分:2)

您可以使用SFINAE,因为非模板重载优于模板重载。这在pre-c ++ 11和c ++ 11中编译:

#include <sstream>
#include <string>
#include <iostream>

using namespace std;

namespace my {
   template <bool V, class T>
   struct enable_if {
   };

   template <class T>
   struct enable_if<true, T> {
      typedef T type;
   };

   template <class T1, class T2>
   struct is_same {
      static const bool value = false;
   };

   template <class T>
   struct is_same<T, T> {
      static const bool value = true;
   };
}

template <class T>
typename my::enable_if<my::is_same<T, int>::value
                      || my::is_same<T, double>::value, string>::type
  to_string(T const& a) {
    string ret;
    stringstream b;
    b << a;
    b >> ret;
    return ret;
}

int main() {
   cout << to_string(2) << endl;
   cout << to_string(3.4) << endl;
}

答案 3 :(得分:1)

您可以将函数放在宏中,如下所示:

#ifndef to_string
#define to_string

//....

#endif

然后,在另一个文件中,写下:

#if __cplusplus >= 201103L
    #undef to_string
#else
    #define to_string
#endif

答案 4 :(得分:0)

Boost.Config有一些macros来检查是否支持/使用C ++ 11功能。