为什么在复制构造函数上使用move构造函数?

时间:2018-11-14 19:12:22

标签: c++ oop

这是一个简单的程序,应该处理一个动态的数字数组,然后过滤掉偶数个元素,然后将它们放入新的数组中,然后在屏幕上打印两个数组。

这是头文件:

#pragma once


namespace filter
{
    class Array
    {
        double *arr;
        int n;

public:
    Array();
    Array(int);
    Array(const Array&);
    Array(Array&&);
    void PutIn();
    void PrintOut() const;
    Array isEven();
    Array filter(const std::function<bool(int)>&) const;
    ~Array();

};
}

然后,这是功能的实现:

#include <iostream>
#include <functional>
#include "Array.h";
using namespace filter;
using namespace std;

Array::Array() :arr(nullptr), n(0)
{ }

Array::Array(int n)
{
    this->n = n;
    arr = new double[n];
}

Array::Array(const Array &a1)
{
    n = a1.n;
    arr = new double[n];
    for (int i = 0; i < n; i++)
        arr[i] = a1.arr[i];
}

Array::Array(Array &&a1)
{
    n = a1.n;
    for (int i = 0; i < n; i++)
        arr[i] = a1.arr[i];
    a1.n = 0;
    a1.arr = nullptr;
}

void Array::PutIn()
{
    cout << "Insert elements:\n";
        for (int i = 0; i < n; i++)
            cin >> arr[i];

}
void Array::PrintOut() const
{
    cout << "\nYour array is :\n";
    for (int i = 0; i < n; i++)
        cout << arr[i] << "\t";
}

Array Array::isEven()
{
    return filter([](int x) { return x % 2; });
}
Array Array::filter(const std::function<bool(int)> &f) const
{
    int b = 0;

    for (int i = 0; i < n; i++)
        if (f(arr[i]) == 0)
            b++;

    Array temp(b);
    b = 0;
    for (int i = 0; i < n; i++)
        if (f(arr[i]) == 0)
        {
            temp.arr[b] = arr[i];
            b++;
        }
    return temp;
}

Array::~Array()
{
    delete[]arr;
    n = 0;
}

最后,这是源代码:

#include <iostream>
#include <functional>
#include "Array.h"
using namespace filter;
using namespace std;




int main()
{

    Array a(5);

    a.PutIn();

    Array b = a.isEven();    //WHY THIS LINE OF CODE INVOKES MOVE CONSTRUCTOR AND NOT COPY CONSTRUCTOR?

    a.PrintOut();
    b.PrintOut();

    getchar();
    getchar();

}

因此,如您所见,这是一个相对简单的程序,需要处理用户输入的包含五个元素的数组,然后创建一个由第一个数组的偶数元素组成的新数组。当我运行它时,它工作正常,但是,这里有一件我不理解的小事情。

如果您查看源代码,请注意我留下我的评论的行,即调用move构造函数的行,但我不知道为什么。那将意味着a.IsEven()是RVALUE,因为move构造函数可与RVALUES一起使用,对吗?谁能解释我为什么这是右值?理解这的正确方法是什么?任何帮助表示赞赏!

1 个答案:

答案 0 :(得分:0)

您关于调用isEven调用move构造函数的假设实际上是不正确的。它也不会调用您的副本构造函数。相反,RVO确保返回的对象是在调用站点直接构造的,因此两者都不是必需的。

Live Demo(无法解决注释中提到的代码中的任何缺陷)。