Is there a reason for overloading statements using the rvalue link?

There is a template vector class (it concerns mathematics, not the container). I need to overload general math operations. Does it make sense to overload as follows:

template <typename T, size_t D>
Vector<T, D> operator+(const Vector<T, D>& left, const Vector<T, D>& right)
{
    std::cout << "operator+(&, &)" << std::endl;
    Vector<T, D> result;

    for (size_t i = 0; i < D; ++i)
        result.data[i] = left.data[i] + right.data[i];

    return result;
}

template <typename T, size_t D>
Vector<T, D>&& operator+(const Vector<T, D>& left, Vector<T, D>&& right)
{
    std::cout << "operator+(&, &&)" << std::endl;
    for (size_t i = 0; i < D; ++i)
        right.data[i] += left.data[i];

    return std::move(right);
}

template <typename T, size_t D>
Vector<T, D>&& operator+(Vector<T, D>&& left, const Vector<T, D>& right)
{
    std::cout << "operator+(&&, &)" << std::endl;
    for (size_t i = 0; i < D; ++i)
        left.data[i] += right.data[i];

    return std::move(left);
}

This works very well with this test code:

auto v1 = math::Vector<int, 10>(1);
auto v2 = math::Vector<int, 10>(7);
auto v3 = v1 + v2;

printVector(v3);

auto v4 = v3 + math::Vector<int, 10>(2);

printVector(v4);

auto v5 = math::Vector<int, 10>(5) + v4;

printVector(v5);

//      ambiguous overload
//      auto v6 = math::Vector<int, 10>(100) + math::Vector<int, 10>(99);

and prints this:

operator+(&, &)
8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 
operator+(&, &&)
10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 
operator+(&&, &)
15, 15, 15, 15, 15, 15, 15, 15, 15, 15,

There is a problem with two rvalue references, but I think it doesn't matter.

Why do I want to do this? Due to performance considerations, theoretically this will work a little faster without creating a new object, but will it? Maybe compilers optimize simple code with operator +(const Vector& left, const Vector& right)and there is no reason to overload rvalue?

+4
2

Vector:

  • , , , .
  • .

, Vector :

template <typename T, size_t D>
class Vector
{
   T data[D];
   // ...
};

, T (, float, int), , . Vector<float, D>, , .

, , Vector. C- , , D .

, Vector std::array<T, D> ( c- ), std::vector<T> ( ). D , std::array std::vector.

.

:

, , , operator+(&,&):

template <typename T, size_t D>
Vector<T, D> operator+(const Vector<T, D>& left, const Vector<T, D>& right)
{
    std::cout << "operator+(&, &)" << std::endl;
    Vector<T, D> result;

    for (size_t i = 0; i < D; ++i)
        result.data[i] = left.data[i] + right.data[i];

    return result;
}

:

template <typename T, size_t D>
Vector<T, D>&& operator+(const Vector<T, D>& left, Vector<T, D>&& right)
{
    std::cout << "operator+(&, &&)" << std::endl;
    for (size_t i = 0; i < D; ++i)
        right.data[i] += left.data[i];

    return std::move(right);
}

Vector, . std::vector, , (operator+(&,&)).

?

, .

, . , , , , , , .

r , Vector , . , .

+1

, ( , , ), rvlaue . std::string , : http://en.cppreference.com/w/cpp/string/basic_string/operator%2B

OP , c-style, . C- - , .

+2

Source: https://habr.com/ru/post/1683284/


All Articles