如何为内置类型的arithmitic操作提升两种模板类型呢?

时间:2015-10-24 21:04:10

标签: c++ templates c++11 arithmetic-expressions type-promotion

如果我有一个通用的结构/类:

template<typename T>
struct Container
{
    T value;
    Container(const Value& value) : value(value) { }
};

我想对其中两个进行操作:

template<typename T, typename U>
Container<T> operator+(const Container<T>& lhs, const Container<U>& rhs)
{
    return Container<T>(lhs.value + rhs.value);
}

问题是如果lhs的类型为Container<int>rhs的类型为Container<float>,那么我将获得Container<int> } 背部。但是,如果我要auto result = 2 + 2.0f,那么resultfloat类型。因此内置类型和自定义类型之间的行为不一致。

那么我如何使用operator+重载并使其返回Container<float>,就像C ++如何使用内置类型处理算术推广一样?

1 个答案:

答案 0 :(得分:6)

如果您使用两种类型的模板中的一种,则可能会对总和的结果产生强制转换。例如,如果您不小心选择int作为目标类型,即使总和结果为float,也会将其转换为所选类型。

无论如何,从C ++ 11开始,您依赖于上面示例中的decltype说明符(或者至少,如果Container::TContainer::U+,则可以这样做为auto运算符定义的类型。

我还使用operator+说明符作为#include <iostream> #include <vector> template<typename T> struct Container { T value; Container(const T& value) : value(value) { } }; template<typename T, typename U> auto operator+(const Container<T>& lhs, const Container<U>& rhs) { return Container<decltype(lhs.value+rhs.value)>{lhs.value + rhs.value}; } int main() { Container<int> c1{1}; Container<float> c2{0.5}; std::cout << (c1+c2).value << std::endl; } 的返回值,因为它可以从C ++ 14开始使用,它确实非常有用。

它遵循上面提到的工作示例:

        <div class="wow fadeInUp content-works"> 
            <span class="text-subtitle" style="font-size: 2em; font-weight: 300; color: #333">Previous Orders</span>
                  <div class="row">
                    <div class="col s12 m6">
                      <div class="card blue-grey darken-1">
                        <div class="card-content white-text">
                          <span class="card-title">Order #1</span>
                          <p>Day - Ammount - Item</p>
                        </div>
                        <div class="card-action">
                          <a href="#">Link to somewhere</a>
                        </div>
                      </div>
                    </div>
                  </div>
        </div>