【问题标题】:c++ template operator overloading std::enable_ifc++模板运算符重载std::enable_if
【发布时间】:2016-02-15 11:52:00
【问题描述】:

我在编译此模板时遇到问题。我只想创建一个操作符,其功能取决于数据类型(int 或 float)。 我不是专家,所以我将不胜感激。

template <class T> struct eq {
  typename std::enable_if<std::is_floating_point<T>::value, T>::type
  operator() (const T& x, const T& y) const {
    T* paux;
    if(sizeof(T) == 4){ //float
      uint32_t val = 0;
      if(x == y){
    val = ~val;
    T* paux = reinterpret_cast<T*>(&val);
    return *paux;
      }
      else{
    T* paux = reinterpret_cast<T*>(&val);
    return *paux;
      }
    }
    else{ //double
      uint64_t val = 0;
      if(x == y){
    val = ~val;
    T* paux = reinterpret_cast<T*>(&val);
    return *paux;
      }
      else{
        T* paux = reinterpret_cast<T*>(&val);
        return *paux;
      }
    }
  }
  typename std::enable_if<std::is_integral<T>::value, T>::type
  operator() (const T& x, const T& y) const {
    return (x==y) ? ~((T)(0)) : ((T)(0));
  }
};

错误代码:

clases.cpp:66:3: error: ‘typename std::enable_if<std::is_integral<_Tp>::value, T>::type eq<T>::operator()(const T&, const T&) const’ cannot be overloaded
   operator() (const T& x, const T& y) const {
   ^
clases.cpp:38:3: error: with ‘typename std::enable_if<std::is_floating_point<_Tp>::value, T>::type eq<T>::operator()(const T&, const T&) const’
   operator() (const T& x, const T& y) const {

【问题讨论】:

  • 没有编译器生成的信息消息或注释来提供有关您为什么收到错误的更多信息? GCC 和 Clang(您似乎正在使用其中之一)在这方面非常擅长。如果有的话,请编辑您的问题以包含这些消息。
  • 我正在使用带有 -std=c++11 标志的 g++ 进行编译。我没有收到更多警告消息。

标签: c++ templates compiler-errors


【解决方案1】:

SFINAE 仅在模板参数位于模板的直接上下文中时发生。一个简单的解决方法是将你的 operator() 函数变成带有默认参数的模板函数:

template <class T> struct eq {
  template<typename U=T>
  typename std::enable_if<std::is_floating_point<U>::value, U>::type
  operator() (const T& x, const T& y) const {
    //...
  }
  template <typename U=T>
  typename std::enable_if<std::is_integral<U>::value, U>::type
  operator() (const T& x, const T& y) const {
    //...
  }
};

也许更简洁的解决方案是提供eq 的两个部分特化;一种用于浮点类型,一种用于整数类型:

template <class T, typename=void> struct eq;

template <class T>
struct eq<T, typename std::enable_if<std::is_floating_point<T>::value>::type> {
  T operator() (const T& x, const T& y) const {
    //...
  }
};

template <class T>
struct eq<T, typename std::enable_if<std::is_integral<T>::value>::type> {
  T operator() (const T& x, const T& y) const {
    //...
  }
};

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-04-28
    • 2023-03-03
    • 2015-09-15
    相关资源
    最近更新 更多