1

这是我当前的代码:

template<int n>
struct N{
    static const int k = (n >= 2) ? (1 + N<n-2>::k) : N<0>::k;
};

template<>
struct N<0>{
    static const int k = 0;
};

以下编译:

int main(int, char *[])
{
    cout << N<2>::k;
    getchar();
}

以下不编译:

int main(int, char *[])
{
    cout << N<1>::k;
    getchar();
}

编译器是否急切地计算 ?: 运算符的正确分支?如果是这样,我怎样才能让它懒惰地评估?

4

3 回答 3

5

如果您要使用模板专业化来执行此操作,这就是我将在整个过程中使用的:

template<int n>
struct N{
    static const int k = 1 + N<n-2>::k;
};

template<>
struct N<1>{
    static const int k = 0;
};

template<>
struct N<0>{
    static const int k = 0;
};

除非您准备使用模板执行此操作,否则我通常更喜欢以下内容:

int constexpr N(int n) { return n/2; }
于 2013-10-14T16:43:30.783 回答
1

为了使这个例子工作:

template<int n>
struct N{
    static const int k = 1 + N<n-2>::k;
};

template<>
struct N<1>{
    static const int k = 0;
};

template<>
struct N<0>{
    static const int k = 0;
};

问题在于N<n-2>。当n=1这将导致无限的模板实例化深度。所以这只是部分地回答了这个问题,但我认为你不能强迫模板被懒惰地评估。

于 2013-10-14T16:43:16.997 回答
1

这似乎可行,并且可以很容易地推广到需要?用惰性求值构造替换三元运算符的情况:

#include <iostream>

template<int n, bool = (n >= 2)>
struct N;

template<>
struct N<0, false>{
    static const int k = 0;
};

template<int n>
struct N<n, true> {
    static const int k = 1 + N<n-2>::k;
};

template<int n>
struct N<n, false> {
    static const int k = N<0>::k;
};

int main() {
    std::cout << N<2>::k << '\n'; 
    std::cout << N<1>::k << '\n';
}

但是,对于 C++11constexpr函数,此实现已过时。

于 2013-10-14T16:45:24.333 回答