为什么需要pair<iterator,bool> insert(value_type&& val); std::set 的插入函数版本

问题描述

嗨,我想了解如何使用带有右值和左值引用作为参数的函数的重载版本。所以这是我写的例子,以更好地理解差异:

car.h

class Car{
    private:
      int number=1000;
      string name="default name";
      std::set<int> Carset;
    public:
       void pushtoset(int &);
       void pushtoset(int &&);

}

car.cpp

#include "car.h"

void Car::pushtocar(int &x){

    Carset.insert(x);
}
void Car::pushtocar(int &&x){
    Carset.insert(x);    
}

ma​​in.cpp

int main(){
    Car object;
    int x = 43;    
object.pushtocar(x); //this calls pushtocar(int&) version(say version I)
object.pushtocar(54); // this calls pushtocar(int &&) version(say version II)
    return 0;

我的问题是在版本 II 的情况下,当此成员函数的主体完成时,并且由于在函数主体内部,参数 x 是左值(对于函数而言是局部的),因此 x 将被销毁。这是否意味着我们插入到集合中的值也会被销毁?如果是这样,我如何防止推送到集合上的值不被销毁?我认为与第一个问题有关的第二个问题是,当我在版本 II 中编写 Carset.insert(x); 时,x 会被复制或移动吗?我认为它会被复制。因此,如果 x 被复制,那么 x 被销毁也没有问题,因为插入的元素和 x 是相互独立的。但是现在如果我写 Carset.insert(std::move(x)); 那么 x 将被“移动”到集合而不是复制。所以在这种情况下,我们会遇到问题,函数体完成后,x 将被销毁,因此插入的元素也将被销毁。有什么方法可以防止在这个移动的情况下插入集合中的元素使 x 处于有效状态被销毁?我对这个概念的理解是否正确?

解决方法

版本 II 采用 'swap' [std::move] 所以完成后,传递给函数的参数是未定义的。你不能再使用它了。右值引用延长了对象的生命周期,它不会被立即销毁。 我采用左值的版本,所以它是复制构造函数。它的正确形式应该是

void Car::pushtocar(const int &x){

    Carset.insert(x);
}