c++ 整数的幂,模板元编程

标签 c++ templates c++11 template-meta-programming

我想做一个返回整数幂的函数。 请阅读 fmuecke 的解决方案 power of an integer in c++ .

但是,我想将他的解决方案推广到任意类型 T。 由于 c++11 有 constexpr,我想这是可能的。

天真地,我尝试了类似的东西,

template<class T, int N>
inline constexpr T pow(const T x){
    return pow<N-1>(x) * x;
}
template<class T>
inline constexpr T pow<T, 1>(const T x){
    return x;
}
template<class T>
inline constexpr T pow<T, 0>(const T x){
    return 1;
}

实际上这种方法失败了,因为函数模板的部分特化是不允许的。

还有一个问题。我听说 constexpr 函数是否在编译时进行评估取决于编译器。 我如何强制它计算通用类型。 我从某处读到,积分 const 最简单的技巧之一是将其包装在 std::integral_const::value 中。

最佳答案

使用递归的解决方案:

#include <iostream>

template<class T>
inline constexpr T pow(const T base, unsigned const exponent)
{
    // (parentheses not required in next line)
    return (exponent == 0) ? 1 : (base * pow(base, exponent-1));
}

int main()
{
    std::cout << "pow(2, 4): " << pow(2, 4) << std::endl;
    std::cout << "pow(5, 0): " << pow(5, 0) << std::endl;
}

Jeremy W. Murphy建议/请求使用平方乘幂的版本:

template<class T>
inline constexpr T pow(const T base, unsigned const exponent)
{
    // (parentheses not required in next line)
    return (exponent == 0)     ? 1 :
           (exponent % 2 == 0) ? pow(base, exponent/2)*pow(base, exponent/2) :
           base * pow(base, (exponent-1)/2) * pow(base, (exponent-1)/2);
}

“我听说 constexpr 函数是否在编译时求值取决于编译器。”

没错,AFAIK。编译器不需要在编译时进行常量初始化,但如果你使用 constexpr 函数的结果作为非类型模板参数,它必须在编译时计算结果。

std::cout << std::integral_constant<int, pow(2, 4)>::value << std::endl;

另见 Andy Prowl 中使用 integral_constant 作为 pow 参数的方法的答案。

以下是强制编译时评估的方法:

#include <iostream>
#include <type_traits>

// insert a constexpr `pow` implementation, e.g. the one from above

template < typename T, T base, unsigned exponent >
using pow_ = std::integral_constant < T, pow(base, exponent) >;

// macro == error prone, you have been warned
#define POW(BASE, EXPONENT) (pow_ < decltype(BASE), BASE, EXPONENT > :: value)

int main()
{
    std::cout << "pow(2, 4): " << pow_<int, 2, 4>::value << std::endl;
    std::cout << "pow(2, 4): " << POW(2, 4) << std::endl;
}

如果您投反对票,请发表评论,以便我改进我的答案。

关于c++ 整数的幂,模板元编程,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/16443682/

相关文章:

C++ 专门化单一成员函数

c++ - 整数在调试器中没有预期值

c++ - FANN 的例子给出了错误的结果,尽管训练看起来很成功

c++ - 测量网络延迟

c++ - OpenMP 在 for 循环中并行化代码块?

javascript - 如何使用 Handlebars 迭代对象?

Django 模板和 latex

c++ - 这是什么疯狂的 C++11 语法 ==> struct : bar {} foo {};?

c++ - 使用 std::shared_ptr 接收变量作为引用的优缺点是什么?

c++11 - 如何从Lambda函数返回nullptr?