根据模板参数比较条件代码

问题描述 投票:0回答:3

大家!想要根据模板参数使方法编译不同。

template <unsigned long prec> class DFixed {
public:
  unsigned long val;
...
  template <unsigned long prec1> DFixed<prec> &operator-=(DFixed<prec1> d) {
    #if prec==prec1
    val -= d.val;
    #elif prec<prec1
    val -= d.val/(prec1/prec);
    #else
    val -= d.val*(prec/prec1);
    #endif
    return *this;
  }
...
};

但是上面的代码即使对于不同的 prec 也会调用 prec==prec1 的 block。

c++ templates conditional-compilation
3个回答
1
投票

正如已经说过的,C++17的

if constexpr
是最好的解决方案:

template <unsigned long prec1>
DFixed & operator-=(DFixed<prec1> d) {
    if constexpr (prec==prec1)
        val -= d.val;
    else if constexpr (prec<prec1)
        val -= d.val/(prec1/prec);
    else
        val -= d.val*(prec/prec1);

    return *this;
}

如果您使用的是 C++11,则可以将 SFINAE 与隐藏在 REQUIRES 宏中的

std::enable_if
一起使用:

#define REQUIRES(...) typename std::enable_if<(__VA_ARGS__), int>::type = 0
template <unsigned long prec1, REQUIRES(prec==prec1)>
DFixed & operator-=(DFixed<prec1> const & d) {
    val -= d.val;
    return *this;
}
template <unsigned long prec1, REQUIRES(prec<prec1)>
DFixed & operator-=(DFixed<prec1> const & d) {
    val -= d.val/(prec1/prec);
    return *this;
}
template <unsigned long prec1, REQUIRES(prec>prec1)>
DFixed & operator-=(DFixed<prec1> const & d) {
    val -= d.val*(prec/prec1);
    return *this;
}

请注意,输入参数

d
是通过
const
引用传递的,以避免不必要的复制。


1
投票

看来你想使用类似的东西

if constexpr (prec == prec1) {
    // one branch
}
else {
    // other branch
}

if constexpr
是随 C++17 引入的。


0
投票

我还有另一个问题,我想根据模板值声明或不声明类参数:

template<unsigned int N,class T>    
union Vec{
    public:
    T array[N];
    struct{
        //if N>0
        T x;
        //if N>1
        T yn;
        //if N>2
        T z;
        //if N>3
        T w;
        };
};

有人知道怎么做吗? 预先感谢。

© www.soinside.com 2019 - 2024. All rights reserved.