Ant*_*ant 6 c++ templates sum c++11
这是来自C++ Primer Chapter 16.2.3(问题16.41)的问题:
写一个sum的版本,其返回类型保证足够大以保存添加的结果.
我敢肯定,有可能是能得到这份工作做了一些默默无闻的STL功能,但在章的背景下,推出标准型转换模板,如remove_reference<T>和make_signed<T>我敢肯定,它打算为我用它来做到这一点,与尾随返回类型一起使用.我能做的最好的事情是:
template <typename It> auto sum(It first, It second) -> typename make_unsigned<It>::type {
    return first+second;
}
这几乎回答了问题,但并不完全,它没有考虑到我可以传递两个unsigned ints的事实,这两个s加上超出了unsigned int可以容纳的值范围(因此循环回零).据我所知,转换模板无法帮助解决这个问题,是否有可能将返回类型推断为从传递的参数推导出的整数类型中的下一个最大整数类型?
由于您希望在编译时执行此操作,因此无法知道函数将被调用的参数的值.因此,您应该在编译时保护再次溢出,并且我想到的最明显的事情是使用促销特征类:
#include <iostream>
#include <limits>
template<typename T>
struct promote;
template<> // and so on for all types that you want to promote
struct promote<unsigned int> // type to be promoted from
{
    using type = unsigned long int; // type to be promoted to
};
// helper a la C++14
template<typename T>
using promote_t = typename promote<T>::type;
template <typename It> 
auto my_sum(It first, It second) -> promote_t<It>
{
    return static_cast<promote_t<It>>(first) + second; // promotion
}
int main()
{
    unsigned int a = std::numeric_limits<unsigned int>::max();
    unsigned int b = std::numeric_limits<unsigned int>::max();
    auto c = my_sum(a, b); // type is promoted to unsigned long int
    std::cout << "a = " << a << std::endl;
    std::cout << "b = " << b << std::endl;
    std::cout << "a + b = " << c << std::endl;
}