初学C++-----------------类的拷贝构造函数

拷贝构造函数能够使类具有自行赋值本类对象的能力,即可生成一个对象的副本,它只以本类对象的引用作为其唯一的形参,该函数的定义形式如下:

class  类名

{

  public:

    类名(形参);//(构造函数)

    类名(类名  &对象名);//(拷贝构造函数)

      ..................

};

类名::类名(类名  &对象名)//拷贝构造函数的实现

{

  函数体

}

拷贝构造函数举例:

class Point

{

  public:

    Point(int xx=0,int yy=0)   //构造函数

  {

      X=xx;

      Y=yy;

    }

    Point(Point &p);   //拷贝构造函数

    int GetX()  {return X;}

    int GetY()  {return Y;}

  private:

    int X,Y;

};

Point::Point(Point &p)

{

  X=p.X;

  Y=p.Y;

cout<<"拷贝构造函数被调用"<<endl;

}

拷贝构造函数被自动调用执行的三种情况:

1) 当用类的一个对象去初始化该类的另一个对象时

void main(void)

{

  Point A(1,2);

  Point B(A);//拷贝构造函数被调用

   cout<<B.GetX()<<endl;

}

2)若函数的形参为类对象,调用函数,实参赋值给形参时

void fun1(Point p)

{

  cout<<p.GetX()<<endl;

}

void main()

{

Point  A(1,2);

fun1(A);//调用拷贝构造函数

}

3) 若函数的返回值是类的对象,函数执行完成返回调用时

Point fun2()

{

  Point A(1,2);

  return A;//调用拷贝构造函数

}

void main()

{

  Point B;

B=fun2();

}

 如果程序员没有为类声明拷贝初始化构造函数,则编译器自己生成一个拷贝构造函数,该函数的功能是:用作为初始值的每个数据成员的值,初始化将要建立的对象的对应的数据成员。

浅拷贝

 由默认的拷贝构造函数将已有的对象的数据成员一一赋值给同类的新对象的各数据成员来构造新对象的方法就是浅拷贝,也即是成员级拷贝。

不足之处:

若用户未提供类的显示拷贝构造函数,而让系统去执行缺省的拷贝构造函数,只进行对象间的原样拷贝,则会出现两个对象拥有同一个资源,即拥有同一块系统堆空间的情况(因为进行了原样拷贝,从而使得两个不同对象的地址值完全相同)。当对象被析构时,则会出现同一资源被释放了两次的错误。

深拷贝

为了克服浅拷贝的不足,用户必须给出显式的拷贝构造函数,以实现“深拷贝”的功能:在拷贝构造函数中,首先要动态申请存储空间,并向该空间拷贝原对象的内容。

显式拷贝构造函数例子:

person(person &p)

{

  cout<<"copying"<<p.pName<<"into its own block"<<endl;

  pName=new char[strlen(p.pName)+1];

strcpy(pName,p.pName);

}

初学C++-----------------类的拷贝构造函数

时间: 2024-08-08 16:21:46

初学C++-----------------类的拷贝构造函数的相关文章

模板类的拷贝构造函数和重载=

http://bbs.csdn.net/topics/190144045 1 #include<iostream> 2 #include<vector> 3 #include<string> 4 5 6 using namespace std; 7 8 template <typename T,size_t size> 9 class fixed_vector 10 { 11 public: 12 typedef T* iterator; 13 typede

C++:派生类的默认构造函数和拷贝构造函数调用基类构造函数的机制(含程序验证)

1.如果基类定义了不带参数的默认构造函数,则编译器为派生类自动生成的默认构造函数会调用基类的默认构造函数. 2.如果基类定义了拷贝构造函数,则编译器为派生类自动生成的拷贝构造函数同样会调用基类的拷贝构造函数. 3.如果基类定义了带参数的构造函数,派生类没有定义任何带参数的构造函数,则不能直接调用基类的带参构造函数,程序编译不通过. 代码如下: #include<iostream> using namespace std; //基类Game,定义了两个构造函数和一个拷贝构造函数 class Ga

组合类、派生类 拷贝构造函数

在派生类中如何写拷贝构造函数 一种形式:派生类拷贝构造函数名(对象p的引用):基类构造函数名(参数列表) 如:student::student(student&p):stud(p.num,p.name,p.sex) //注意,参数形式,是对象的引用,我们知道引用是C++特有的,这又是一个引用的用法 呵呵 一种形式:派生类拷贝构造函数名(对象p的引用):基类拷贝构造函数名(p) 如:student::student(student &p):stud( p) 注意:在调用基类的构造函数时或拷贝

类和对象(7)—— 拷贝构造函数应用场景

#define _CRT_SECURE_NO_WARNINGS #include <iostream> using namespace std; class Test { public: //显示的无参数的构造函数 Test() { cout << "Test()..." << endl; m_x = 0; m_y = 0; } //显式地有参数的构造函数 Test(int x, int y) { cout << "Test(i

C++的拷贝构造函数

1?  类会提供默认的拷贝构造函数 –默认的拷贝构造函数会完成所有成员的逐个复制 2?  拷贝构造的调用时机: –函数值传递时 –函数返回时 –用同类型的对象初始时 3?  何时需要自定义拷贝构造函数? –类中有指针(或引用 )成员时 –希望自定义对象的拷贝过程时 4?  使用匿名对象简化编程 // // main.cpp // 拷贝构造函数 // // Created by 06 on 15/1/26. // Copyright (c) 2015年 黄永锐. All rights reserv

第五篇:明确拒绝不想编译器自动生成的拷贝构造函数和赋值运算符重载函数

前言 如果你不想要编译器帮你自动生成的拷贝机制 (参考前文),那么你应当明确的拒绝. 如何拒绝?这便是本文要解决的主要问题. 问题描述 当你定义了一个类,而这个类中各对象之间也是封装的 - 禁止同类对象之间的相互赋值以及复制,那么你需要屏蔽掉编译器帮你生成的拷贝构造函数以及赋值运算符. 在许多代码中,会看到通过将拷贝构造函数和赋值运算符重载函数声明为私有且不予实现来实现这个功能.然而,这不是最科学的做法. 因为这没有做到真正的屏蔽:你在自己的成员函数中,或者友元函数中仍然可以调用这两个私有函数,

[QT入门篇]3 QObject的拷贝构造函数与赋值运算符

本文主要是针对QObject的拷贝构造函数和赋值运算符进行说明.先来看一下拷贝构造函数定义:拷贝构造函数,又称复制构造函数,是一种特殊的构造函数,它由编译器调用来完成一些基于同一类的其他对象的构建及初始化.其唯一的形参必须是引用,但并不限制为const,一般普遍的会加上const限制.此函数经常用在函数调用时用户定义类型的值传递及返回.拷贝构造函数要调用基类的拷贝构造函数和成员函数.如果可以的话,它将用常量方式调用,另外,也可以用非常量方式调用. 还记得<[QT入门篇]1 QT中的对象模型>中

明确拒绝不想编译器自动生成的拷贝构造函数和赋值运算符重载函数

前言 如果你不想要编译器帮你自动生成的拷贝机制 (参考前文),那么你应当明确的拒绝. 如何拒绝?这便是本文要解决的主要问题. 问题描述 当你定义了一个类,而这个类中各对象之间也是封装的 - 禁止同类对象之间的相互赋值以及复制,那么你需要屏蔽掉编译器帮你生成的拷贝构造函数以及赋值运算符. 在许多代码中,会看到通过将拷贝构造函数和赋值运算符重载函数声明为私有且不予实现来实现这个功能.然而,这不是最科学的做法. 因为这没有做到真正的屏蔽:你在自己的成员函数中,或者友元函数中仍然可以调用这两个私有函数,

不使用编译器自动生成的拷贝构造函数和赋值运算符的方法

方法1:声明私有的拷贝构造函数和赋值运算符,这样不但阻止了编译器生成默认版本,并且使得用户无法调用他们,但是这时成员函数和友元函数还是可以调用他们,为了阻止他们的调用可以不定义这些私有的拷贝构造函数和赋值运算符.(标准库中也是如此阻止拷贝的) 代码段1.1:HomeForSale.h文件 #ifndef HOMEFORSALE_H #define HOMEFORSALE_H class CHomeForSale { public: CHomeForSale(){} private: CHomeF