从现有对象创建对象

时间:2013-11-07 09:24:50

标签: c++ oop c++11 copy-constructor assignment-operator

为什么以下程序的输出是200-200?这里只是更改object2成员变量值。

class X
{
private:
   int *m_plnt;

public:
   X():m_plnt(new int()){}
   X(const X & rhs)
   {
      m_plnt = rhs.m_plnt;
   }
   void setvalue(int value) { *m_plnt = value; }

   int getvalue(){return *m_plnt;}
};

int main()
{
   X obj1;
   obj1.setvalue(100);
   X obj2(obj1); 
   obj2.setvalue(200); // how its changing obj1.m_plnt value
   return 0;
}

4 个答案:

答案 0 :(得分:2)

  

为什么以下程序的输出是200-200?

因为你只有一个整数和两个指针。

  

这里只是更改object2成员变量值。

不,你没有改变成员变量;你正在改变它指向的价值。两个类都包含指向同一整数的指针。没有课程,你可以更清楚地看到这一点;它和

完全一样
int * p1 = new int();  // Create an integer
*p1 = 100;
int * p2 = p1;         // Point to the same integer
*p2 = 200;

答案 1 :(得分:1)

当您复制obj1时,您正在获取指针的副本,因此obj1和obj2指向相同的值。

答案 2 :(得分:1)

类定义包含具有int指针类型的数据成员。在使用复制构造函数期间,此指针的值将从原始对象复制到爬行对象。因此,两个对象都有指向相同内存地址的指针,即两个对象共享相同的内存位置。该计划的输出证明了这一事实。 您可以更改复制构造函数,以便分配新内存。例如

X(const X & rhs) : m_plnt(new int(*rhs.m_plnt)) { }

在这种情况下,新对象有自己分配的内存,原始对象的更改不会影响新对象。

答案 3 :(得分:1)

正如大家已经提到的,你正在使用指针,所以当你调用你的复制构造函数时,你所做的只是将rhs.m_plnt的地址分配给this.m_plant的地址。这意味着对任一对象的任何更改都将导致对另一个对象的更改。

另外,因为您似乎不需要动态的整数数组,所以不需要任何指针。看看这段代码:

#include <iostream>

class X
{
private:
   int m_plnt;

public:
   X():m_plnt(int()){}
   X(const X & rhs)
   {
      m_plnt = rhs.m_plnt;
   }
   void setvalue(int value) { m_plnt = value; }

   int getvalue(){return m_plnt;}
};

int main()
{
   X obj1;
   obj1.setvalue(100);
   X obj2(obj1); 
   obj2.setvalue(200); // how its changing obj1.m_plnt value
   std::cout << obj1.getvalue() << "-" << obj2.getvalue() << std::endl;
   return 0;
}

这将输出:

100-200