`

对构造函数、拷贝构造函数和赋值操作符调用的简单回顾

阅读更多

本文只是测试构造函数、拷贝构造函数和赋值操作符的调用问题,不涉及这些函数内的具体实现,所以多包涵

还有如果觉得有不足之处还望指出,谢谢…………

 

 

#include<iostream>

using namespace std;

class Object{  
	
 	 char* name;
public:
	Object() 
	{
		cout << "Objected is constructed.(无参数)" << endl; 
	}

	Object(char* s) //
	{
		name = s;//
		cout << "Objected is constructed.(参数)" << endl; 
	}

	Object( const Object& o) 
	{
//为对象申请内存并进行出错检查;(本文没有处理)
//从对象o复制到本对象
		name = o.name;
		cout << "Object is copied." << endl; 
	}

	char* getName() 
	{ 
		return name;
	}
	Object & operator = (const Object& lala)
	{
		name = lala.name;
		cout << "Object is operator =." << endl; 

		return *this;
	}

	~Object()
	{ 
		cout << "Object is destructed." << endl;
	}


};

Object getObject( Object o)
{ 
	cout << "getO" << endl;//

	return o; 
}

Object getObject1( Object& o)
{ 
	cout << "getO1" << endl;//

	return o; 
}

Object& getObject2( Object& o)
{ 
	cout << "getO2" << endl;//

	return o; 
}


int main()
{

	Object o("zhangsan");

	Object o1;
	o1 = getObject( o);
	cout << endl;

	cout << "Object o2 = getObject(o):" << endl;
	Object o2 = getObject(o);//相当于Object o2(getObject(o));
	cout << endl;

	cout << "o1 = getObject(o):" << endl;
	o1 = getObject(o); 
	cout << endl << endl;

//getObject1
	cout << "getObject1:" << endl;
	Object o11;
	o11 = getObject1( o);
	cout << endl;

	cout << "Object o22 = getObject(o):" << endl;
	Object o22 = getObject1(o);
	cout << endl;

	cout << "o11 = getObject(o):" << endl;
	o11 = getObject(o);
	cout << endl << endl;

//getObject2
	cout << "getObject2:" << endl;
	Object o111;
	o111 = getObject2( o);
	cout << endl;

	cout << "Object o222 = getObject(o):" << endl;
	Object o222 = getObject2(o);
	cout << endl;

	cout << "o111 = getObject(o):" << endl;
	o111 = getObject(o);

	cout << "end" << endl;

	return 0;
}
 

 

 

Objected is constructed.(参数)

Objected is constructed.(无参数)

Object is copied.           //每次传参都会构建临时对象

getO

Object is copied.

Object is destructed.

Object is operator =.

Object is destructed.

 

Object o2 = getObject(o):

Object is copied.

getO

Object is copied.

Object is destructed.

 

o1 = getObject(o):

Object is copied.

getO

Object is copied.

Object is destructed.

Object is operator =.

Object is destructed.

 

 

getObject1:

Objected is constructed.(无参数)

getO1

Object is copied.

Object is operator =.

Object is destructed.

 

Object o22 = getObject(o):

getO1

Object is copied.

 

o11 = getObject(o):

Object is copied.

getO

Object is copied.

Object is destructed.

Object is operator =.

Object is destructed.

 

 

getObject2:

Objected is constructed.(无参数)

getO2

Object is operator =.

 

Object o222 = getObject(o):

getO2

Object is copied.

 

o111 = getObject(o):

Object is copied.

getO

Object is copied.

Object is destructed.

Object is operator =.

Object is destructed.

end


拷贝构造函数和赋值操作符:

同样是利用现有对象的值,生成/更新另一个对象的值。
区别在于:拷贝构造函数是去完成对未初始化的存储区的初始化,而赋值操作符则是处理一个已经存在的对象。对一个对象赋值,当它一次出现时,它将调用拷贝构造函数,以后每次出现,都调用赋值操作符。

定义对象a,并用另一个对象b对a进行初始化时,
若没有拷贝构造函数时,那么编译器会自动生成一个
T b(1);//假设对象b已经初始化
T a(b);//初始化阶段,调用拷贝构造函数
T c = b;//虽然使用了“=”,但是初始化阶段,仍调用拷贝构造函数
c = a; //因为对象c已经定义,所以此处调用赋值操作符重载函数。如果没有编译器会自动生成一个。 

 

1
1
分享到:
评论
2 楼 synchronized_lala 2012-11-21  
lazy_ 写道

好激动,有人回复了,而且那么详细。像你开始说的,我其实只能自己理解,觉得有点写不清楚。而且你比我理解的深刻,至于后面提到的copy constructor参数为什么是引用类型,我还么考虑到呢,嘻嘻……
你说的指针和引用类型的区别分享的网址我明天就去好好研究一下,你说学java比我学C++还……不过我这水平我也不好意思说自己学C++的了,呵呵
谢谢你的回复,
1 楼 lazy_ 2012-11-21  
我用1个小时实验了你的程序。感觉你的总结看起有点难受。。。
你是想说明以下的问题而已吧?博主看看我有没有理解错。工作我也写一小部分C++。。。JAVA、JS才是我的主行。

1.
Object o("zero");
Object o1;
o1 = o;


Object o("zero");
Object o1= o;


是不同的。

前者会调用operator=,而后者会调用copy conostructor。后者相当于调用constructor(object&)。为什么后者会调用copy constructor?后者o1只是变量名而已,几乎是没有什么意义的,遇到'=',从逻辑上只可能做个简单的引用操作或复制操作,是复制还是引用呢?C++提供了两种语法,Object& o1 = o;表示引用,而Object o1 = o1表示复制,相对地JAVA,比较简洁,只提供了引用的方式。而前者的o1是个对象,遇到'=',理所当然地会调用自身的operator=方法了。


其次就是一些基本的知识:

函数的形参是对象引用的话,那么调用该函数,准备参数时不会调用copy constructor;
函数的形参是对象的话,那么调用该函数,准备参数时会调用copy constructor;

函数的返回值是对象引用的话,那么函数返回时不会调用copy constructor;
函数的返回值是对象的话,那么函数返回是会调用copy constructor。


在学习博主的代码的过程中,我在想,为什么copy constructor的参数是个引用,而不是普通的传值呢?想想,其实好简单的道理,我在写一个object的copy constructor,如果一个方法调用使用该object作为形参,那么copy constructor 就会被调用。当然copy constructor本身也是个方法,如果copy 也是以object作为形参,那么岂不是“死循环”了——copy constructor调用copy constructor,没完没了啊?

同时也重温了下引用和指针。
看了http://www.uml.org.cn/c++/201010123.asp 的分析,恍然大悟啊。。。
原来引用和指针本质是一样的东西,都是存放目标的地址值,只是操作这两种类型的时候,编译器执行不同的操作。操作引用的时候,会间接寻址,操作寻址后的对象,而操作指针,就是操作地址值本身,而不是地址值指向的地方。

相关推荐

    拷贝构造函数和赋值操作符号的重载.pdf

    在C++编程中,拷贝构造函数和赋值操作符重载是两个非常重要的概念,尤其是在处理包含动态分配内存的类时。拷贝构造函数和赋值操作符的正确实现对于确保对象之间的独立性和防止资源泄露至关重要。 拷贝构造函数是一...

    拷贝构造函数和赋值操作符号的重载.docx

    在C++编程中,拷贝构造函数和赋值操作符重载是两个非常重要的概念,尤其是在处理包含动态分配资源的对象时。拷贝构造函数和赋值操作符是保证对象正确复制和赋值的关键。 拷贝构造函数是一种特殊的构造函数,其主要...

    构造函数和复制构造函数

    拷贝构造函数通常用于对象之间的复制操作,如对象的初始化、赋值操作符等。 在上面的代码中,我们定义了一个名为classA的类,其中包括一个默认构造函数、一个带参数的构造函数、一个复制构造函数、一个赋值操作符和...

    深入C++中构造函数、拷贝构造函数、赋值操作符、析构函数的调用过程总结

    例如,如果你的类管理着动态分配的内存或系统资源,你必须确保构造函数、拷贝构造函数和赋值操作符都被正确地重载以实现深拷贝或浅拷贝,同时析构函数也要负责释放相应的资源。 总的来说,理解这些构造和析构过程有...

    关于拷贝构造函数和赋值运算符

    在编程中,包含动态分配成员的类需要提供拷贝构造函数,并重载“=”赋值操作符,以避免对象之间的不独立和隐患。 一、拷贝构造函数 拷贝构造函数是一种特殊的构造函数,它在对象建立时被调用,以复制指针所指向的...

    关于拷贝构造函数和赋值函数.txt

    在C++编程语言中,拷贝构造函数和赋值操作符是两个非常重要的概念,它们主要用于处理类的对象之间数据的复制问题。下面将对这两个概念进行详细介绍。 ### 拷贝构造函数 拷贝构造函数是一种特殊的构造函数,它用于...

    详解C++ 拷贝构造函数和赋值运算符

    在C++中,良好的编程习惯要求赋值运算符(又称拷贝赋值操作符)应该实现“自赋值安全”和“右结合性”,即`a = a`应保持不变,且连续赋值如`a = b = c`应正确工作。 深拷贝和浅拷贝是拷贝过程中涉及到的一个关键...

    C++中复制构造函数和重载赋值操作符总结

    这篇文章将对C++中复制构造函数和重载赋值操作符进行总结,包括以下内容: 1.复制构造函数和重载赋值操作符的定义; 2.复制构造函数和重载赋值操作符的调用时机; 3.复制构造函数和重载赋值操作符的实现要点; 4....

    c++中拷贝构造函数实例

    - **拷贝初始化**:通过等号操作符`= new MyClass(obj)`创建对象时,调用的是拷贝构造函数。 - **赋值操作**:而当使用`= operator`为已有对象赋值时,调用的是赋值运算符`=`。这两个过程虽然类似,但不是一回事,...

    1. 拷贝构造与拷贝赋值1

    拷贝构造和拷贝赋值是面向对象编程中两种重要的对象复制方式,它们在C++、Java和Python等编程语言中都有所体现,但实现机制和...程序员应根据类的特性决定是否需要自定义拷贝构造函数和拷贝赋值操作符以实现深拷贝。

    C++ 赋值构造函数注意点介绍

    初始化和赋值问题详解C++ 拷贝构造函数和赋值运算符详解C++中对构造函数和赋值运算符的复制和移动操作C++中复制构造函数和重载赋值操作符总结深入C++中构造函数、拷贝构造函数、赋值操作符、析构函数的调用过程总结...

    c++构造函数和析构函数,拷贝,重载

    根据给定的文件标题“C++构造函数和析构函数,拷贝,重载”以及描述“一道很好的习题代码,包含构造、析构、拷贝、重载”,我们可以了解到这段代码主要涉及到了C++中类的设计与实现,特别是构造函数、析构函数、拷贝...

    2.4+拷贝构造函数1

    此外,当一个对象作为右值出现在赋值操作符右边时,也可能调用拷贝构造函数,如`Point p3; p3 = p1;`。但是,C++11引入了移动语义,使得在这种情况下更倾向于使用移动构造函数,而不是拷贝构造函数。 需要注意的是...

    拷贝构造函数详解VC共12页.pdf.zip

    需要注意的是,拷贝构造函数和赋值操作符(=运算符)在处理资源管理时常常需要一起考虑,因为两者都会涉及到对象的复制。有时,为了遵循“规则-of-three/five/six”,我们需要为类提供一个自定义的赋值操作符,以...

    析构或构造函数声明为保护或私有成员

    在上面的代码中,类 A 的拷贝构造函数和 operator=(赋值操作符重载)被声明为私有成员,以禁止外部用户对对象进行复制动作。 将构造函数和析构函数声明为私有或保护成员是一种常用的设计模式,可以用于实现 ...

    C++规定与类同名的函数就是拷贝构造函数

    类的基本特性包括构造函数和拷贝构造函数,其中构造函数用于初始化新创建的对象,而拷贝构造函数则用于复制对象。静态成员是属于类而非类的特定实例的,它们可以被所有对象共享,且可以被静态成员函数访问。友元机制...

    string 类实现,构造函数、析构函数、操作符重载等

    通过以上分析,我们可以看到`String`类的设计和实现涵盖了构造函数、析构函数以及多种操作符重载等功能,使得该类能够有效地处理字符串数据。对于学习C++语言的新手来说,这是一个很好的实践项目,可以帮助他们更好...

Global site tag (gtag.js) - Google Analytics