c++调用拷贝构造函数数是怎么调用的

C++中如何区别=调用的是拷贝构造函数还是拷贝赋值运算符?
[问题点数:40分,结帖人NineTyNine_LP]
C++中如何区别=调用的是拷贝构造函数还是拷贝赋值运算符?
[问题点数:40分,结帖人NineTyNine_LP]
不显示删除回复
显示所有回复
显示星级回复
显示得分回复
只显示楼主
2013年 总版技术专家分年内排行榜第三
2012年 总版技术专家分年内排行榜第七
2013年 总版技术专家分年内排行榜第三
2012年 总版技术专家分年内排行榜第七
2014年10月 C/C++大版内专家分月排行榜第三2014年4月 C/C++大版内专家分月排行榜第三
2013年 总版技术专家分年内排行榜第三
2012年 总版技术专家分年内排行榜第七
匿名用户不能发表回复!|
每天回帖即可获得10分可用分!小技巧:
你还可以输入10000个字符
(Ctrl+Enter)
请遵守CSDN,不得违反国家法律法规。
转载文章请注明出自“CSDN(www.csdn.net)”。如是商业用途请联系原作者。c++ explicit 拷贝构造函数
c++ explicit 拷贝构造函数
#include &iostream&#include &fstream&#include &string&class a{public:&explicit a(int ii=0):i(ii){}&explicit& a(const a& aa){i=aa.i;}&void echo(const a& ii){cout&&ii.i&&}private:&};int main(){&&//a bb=&return 0;}
//a bb=为什么会出错,bb和aa都是a类型,那里还会出现隐式转换?
1:为什么会出错,bb和aa都是a类型,哪里出现了隐式转换?
2:难道用"="号初始化都就算是隐式转换?关键是没有类型转换啊?
理解有误,explicit指的是防止隐式调用你的拷贝构造函数,a bb=这种方法中,bb隐式调用了他自己的拷贝构造函数,所以不可以;如果改为a bb(aa);这样调用就是显式调用,就可以。并不是你理解的类型转换。
恩,如果此类里面echo函数去掉引用,改为 void echo(a ii){cout&&ii.i&&},主函数里怎么调用?如果aa是做它的参数如何写?
不加引用时,echo函数的参数会隐式调用拷贝构造函数,只能把拷贝构造里的explicit关键字去掉了。加引用时,以aa做参数为例,传入的只aa的别名,不再存在拷贝改造了,这点也可以看出函数参数传引用效率会更高。
非常感谢,我的最终疑问是我发现一个问题,凡是值传递,都会隐式调用,是这样的吗?关键隐式调用我还有点模糊,
a bb=aa 这为什么会是隐式调用?难道凡是没以括号形式调用构造函数,就算隐式调用?
a bb=aa中bb是一个新对象,所以他肯定会调一个构造函数,或是默认构造,或是拷贝构造,至于为啥调拷贝构造就是这么设计的呗,另外,除括号形式调用构造函数,显示调用还包括new的对象,a* bb = new a(aa)这样也是显示调用,你可以试试。
相关知识等待您来回答
编程领域专家
& &SOGOU - 京ICP证050897号1571人阅读
c/c++(33)
c/c++(34)
#include&iostream&class Time{&int hour,minute,public:&Time():hour(0),minute(0),second(0)&{};&Time(Time &t);&void getTime();&void setTime(int h,int m,int s);
};Time::Time(Time &t){&hour=t.&minute=t.&second=t.&cout&&"Notice!!! Copy constructor is being called."&&}void Time::getTime(){&cout&&"Now the time is"&&hour&&":"&&minute&&":"&&second&&}void Time::setTime(int h,int m,int s){&if(m&0||m&59||s&0||s&59||h&0||h&23)&{&&cout&&"Error!Please Check!"&&&&&}&hour=h;&minute=m;&second=s;}void fun0(Time t){
}Time fun1(){&T&}void main(){&Time time0;&time0.setTime(12,5,7);&Time time1(time0);&time1.getTime();&fun0(time0);&Time time2;&time2=fun1();}
通常构造函数只在对象创建时被调用,而拷贝构造函数则在以下3种情况下被调用。
1。当使用类的一个对象去初始化该类的另一个新对象时。
2。如果函数的形参是类的对象,那么当调用该函数时拷贝构造函数也会被调用。
3。如果函数的返回值是类的对象,那么函数执行完成返回调用者时。
* 以上用户言论只代表其个人观点,不代表CSDN网站的观点或立场
访问:137251次
积分:2056
积分:2056
排名:第11960名
原创:51篇
转载:35篇
评论:92条
(1)(1)(1)(1)(1)(2)(1)(3)(3)(2)(1)(5)(16)(27)(4)(11)(6)下次自动登录
现在的位置:
& 综合 & 正文
[互联网面试笔试汇总C/C++-22] 拷贝构造函数调用的时机-完美世界
题目:下面哪种情况下不会调用拷贝构造函数?
A:当用类的一个对象初始化该类的另一个对象时
B:如果函数的形参是类的对象,调用函数时,进行形参和实参结合时
C:如果函数的返回值是类的对象,函数执行完成返回调用者时
D:用类的一个对象给另一个对象赋值的时
A:当用类的一个对象初始化该类的另一个对象时.例如:
int main()
point A(1,2);
point B(A);//用对象A初始化对象B,拷贝构造函数被调用.
point C = A;//这个也是属于用A初始化C,拷贝构造函数被调用,请区别与D
point *D = new point(A);//这个也是属于用A初始化C,拷贝构造函数被调用
B: 如果函数的形参是类的对象,调用函数时,进行形参和实参结合时.
void f(point p)
point A(1,2);
f(A);//函数的形参为类的对象时,当调用函数时,拷贝构造函数被调用.
C:如果函数的返回值是类的对象,函数执行完成返回调用者时
point A(1,2);
return A;//函数的返回值是类的对象,返回函数值时,调用拷贝构造函数.
void main()
D:用类的一个对象给另一个对象赋值的时
int main()
point A,B;
A = B;//这个属于赋值,请区别于A,这种情况下使用的是类的=运算符,而并不是拷贝构造函数。
PS:另外还有一种情况会调用拷贝构造函数,那就是需要产生一个临时类对象时。
&&&&推荐文章:
【上篇】【下篇】比特客户端
您的位置:
详解大数据
详解大数据
详解大数据
详解大数据
C++构造函数和拷贝构造函数详解
关键字:C++
  构造函数、析构函数与赋值函数是每个类最基本的函数。它们太普通以致让人容易麻痹大意,其实这些貌似简单的函数就象没有顶盖的下水道那样危险。
  每个类只有一个析构函数和一个赋值函数,但可以有多个构造函数(包含一个拷贝构造函数,其它的称为普通构造函数)。
  对于任意一个类A,如果不想编写上述函数,C++编译器将自动为A 产生四个缺省的函数,例如:
  A(void); // 缺省的无参数构造函数
  A(const A &a); // 缺省的拷贝构造函数
  ~A(void); // 缺省的析构函数
  A & operate =(const A &a); // 缺省的赋值函数
  这不禁让人疑惑,既然能自动生成函数,为什么还要程序员编写?原因如下:
  &1& 如果使用“缺省的无参数构造函数”和“缺省的析构函数”,等于放弃了自主“初始化”和“清除”的机会,C++发明人Stroustrup 的好心好意白费了。
  &2& “缺省的拷贝构造函数”和“缺省的赋值函数”均采用“位拷贝”而非“值拷贝”的方式来实现,倘若类中含有指针变量,这两个函数注定将出错。
  C++ 默认构造函数 :
  1、每个类必须有一个构造函数,否则没法创建对象;2、若 程序员没有提供任何构造函数,则 C++提供一个默认的构造函数,该默认构造函数是无参构造函数,它仅负责创建对象,不做任何初始化的工作;3、只要 programer 定义了一个构造函数(不管是无参还是有参构造),C++就不再提供默认的默认构造函数。即如果为类定义了一个带参的构造函数,还想要无参构造函数,就必须自己定义;4、与变量定义类似,在用默认构造函数创建对象时,如果创建的是全局对象或静态对象,则对象的位模式全为 0,否则,对象值是随机的。
  C++默认拷贝构造函数:
  1、默认的拷贝构造函数执行的顺序与其他用户定义的构造函数相同,执行先父类后子类的构造。
  2、拷贝构造函数对类中每一个数据成员执行成员拷贝(memberwise Copy)的动作。
  3、如果数据成员为某一个类的实例,那么调用此类的拷贝构造函数。
  4、如果数据成员是一个数组,对数组的每一个执行按位拷贝。
  5、如果数据成员是一个数量,如int,double,那么调用系统内建的赋值运算符对其进行赋值。
  请看下面代码:
  view plain //============================================================================ // Name : main.cpp // Author : ShiGuang // Version :// Copyright :sg131971@.com// Description : Hello World in C++, Ansi-style //============================================================================ #include #include class Student { public:Student()
  { cout && "构造函数1" &&} Student(int k)
  { cout && "构造函数2" &&i =} Student(Student const &m)
  { cout && "拷贝构造函数" &&i = m.i * (-1);} void p()
  { cout && i &&} ~Student()
  { cout && "析构函数" &&} protected:};int main(int argc, char **argv)
  { Student s(9818);// 调用构造函数2 s.p();Student t(s);// 调用拷贝构造函数t.p();Student k =// 调用拷贝构造函数k.p();Student *p = new Student(s);// 调用拷贝构造函数p-&p();S// 调用构造函数1 m =// 赋值运算m.p();return 0;}运行结果:view plain构造函数2 9818拷贝构造函数-9818拷贝构造函数-9818拷贝构造函数-9818构造函数1 9818析构函数下面我们来讨论一下关于浅拷贝和深拷贝的问题。
  深拷贝和浅拷贝的定义可以简单理解成:如果一个类拥有资源(堆,或者是其它系统资源),当这个类的对象发生复制过程的时候(复制指针所指向的值),这个过程就可以叫做深拷贝,反之对象存在资源但复制过程并未复制资源(只复制了指针所指的地址)的情况视为浅拷贝。
  很多人会问到,既然系统会自动提供一个默认的拷贝构造函数来处理复制,那么我们没有必要去自定义拷贝构造函数呀,对,就普通情况而言这的确是没有必要的,但在某些状况下,类体内的成员是需要开辟动态堆内存的,如果我们不自定义拷贝构造函数而让系统自己处理,那么就会导致堆内存的所属权产生混乱。试想一下,已经开辟的一端堆地址原来是属于对象a的,由于复制过程发生,b对象取得是a已经开辟的堆地址,一旦程序产生析构,释放堆的时候,计算机不清楚这段地址是真正属于谁的,当连续发生两次析构的时候就出现了运行错误。
  为了更详细的说明问题,请看如下的代码。
  view plain //============================================================================ // Name : main.cpp // Author : ShiGuang // Version :// Copyright : // Description : Hello World in C++, Ansi-style //============================================================================ #include #include class aa { public:aa()
  { cout && "调用构造函数" &&f = new char[10];} ~aa()
  { cout && "调用析构函数" &&delete[]} char *};int main(int argc, char **argv)
  {printf("p.f=%p\n",p.f);strcpy(p.f, "Computer");cout && p.f &&aa q(p);// 调用默认的拷贝构造函数printf("q.f=%p\n",q.f);cout && q.f &&strcpy(p.f, "Software");cout && p.f &&cout && q.f &&strcpy(q.f, "Software");cout && p.f &&cout && q.f &&return 0;}运行结果:view plain调用构造函数p.f=003F1048 Computer q.f=003F1048 Computer Software调用析构函数通过上面的例子,我们能清楚的看到,第二个对象调用拷贝构造函数,q.f获得的地址值与p.f相同,即指向了同一片内存区域。程序结束时,会两次调用析构函数,即同一个指针执行两遍delete操作,会发生什么呢?这可能是一场灾难,可能会破坏该堆及自由内存表。
  那我们该如何避免呢?这里我们就需要使用深拷贝。
  view plain //============================================================================ // Name : main.cpp // Author : ShiGuang // Version :// Copyright : // Description : Hello World in C++, Ansi-style //============================================================================ #include #include class aa { public:aa()
  { cout && "调用构造函数" &&f = new char[10];} aa(aa const & s)
  { cout && "调用拷贝构造函数" &&f = new char[10];strcpy(f, s.f);} ~aa()
  { cout && "调用析构函数" &&delete[]} char *};int main(int argc, char **argv)
  {printf("p.f=%p\n", p.f);strcpy(p.f, "Computer");cout && p.f &&aa q(p);// 调用用舻目奖垂乖旌printf("q.f=%p\n", q.f);cout && q.f &&strcpy(p.f, "Software");cout && p.f &&cout && q.f &&strcpy(q.f, "Software");cout && p.f &&cout && q.f &&return 0;}运行结果:
  view plain调用构造函数p.f= Computer调用拷贝构造函数q.f= Computer Software Computer Software调用析构函数现在我们可以看到,p.f和q.f分别指向不同的内存区域。
[ 责任编辑:之极 ]
新经济、新业态环境下,数据量呈…
甲骨文的云战略已经完成第一阶段…
软件信息化周刊
比特软件信息化周刊提供以数据库、操作系统和管理软件为重点的全面软件信息化产业热点、应用方案推荐、实用技巧分享等。以最新的软件资讯,最新的软件技巧,最新的软件与服务业内动态来为IT用户找到软捷径。
商务办公周刊
比特商务周刊是一个及行业资讯、深度分析、企业导购等为一体的综合性周刊。其中,与中国计量科学研究院合力打造的比特实验室可以为商业用户提供最权威的采购指南。是企业用户不可缺少的智选周刊!
比特网络周刊向企业网管员以及网络技术和产品使用者提供关于网络产业动态、技术热点、组网、建网、网络管理、网络运维等最新技术和实用技巧,帮助网管答疑解惑,成为网管好帮手。
服务器周刊
比特服务器周刊作为比特网的重点频道之一,主要关注x86服务器,RISC架构服务器以及高性能计算机行业的产品及发展动态。通过最独到的编辑观点和业界动态分析,让您第一时间了解服务器行业的趋势。
比特存储周刊长期以来,为读者提供企业存储领域高质量的原创内容,及时、全面的资讯、技术、方案以及案例文章,力求成为业界领先的存储媒体。比特存储周刊始终致力于用户的企业信息化建设、存储业务、数据保护与容灾构建以及数据管理部署等方面服务。
比特安全周刊通过专业的信息安全内容建设,为企业级用户打造最具商业价值的信息沟通平台,并为安全厂商提供多层面、多维度的媒体宣传手段。与其他同类网站信息安全内容相比,比特安全周刊运作模式更加独立,对信息安全界的动态新闻更新更快。
新闻中心热点推荐
新闻中心以独特视角精选一周内最具影响力的行业重大事件或圈内精彩故事,为企业级用户打造重点突出,可读性强,商业价值高的信息共享平台;同时为互联网、IT业界及通信厂商提供一条精准快捷,渗透力强,覆盖面广的媒体传播途径。
云计算周刊
比特云计算周刊关注云计算产业热点技术应用与趋势发展,全方位报道云计算领域最新动态。为用户与企业架设起沟通交流平台。包括IaaS、PaaS、SaaS各种不同的服务类型以及相关的安全与管理内容介绍。
CIO俱乐部周刊
比特CIO俱乐部周刊以大量高端CIO沙龙或专题研讨会以及对明星CIO的深入采访为依托,汇聚中国500强CIO的集体智慧。旨为中国杰出的CIO提供一个良好的互融互通 、促进交流的平台,并持续提供丰富的资讯和服务,探讨信息化建设,推动中国信息化发展引领CIO未来职业发展。
IT专家新闻邮件长期以来,以定向、分众、整合的商业模式,为企业IT专业人士以及IT系统采购决策者提供高质量的原创内容,包括IT新闻、评论、专家答疑、技巧和白皮书。此外,IT专家网还为读者提供包括咨询、社区、论坛、线下会议、读者沙龙等多种服务。
X周刊是一份IT人的技术娱乐周刊,给用户实时传递I最新T资讯、IT段子、技术技巧、畅销书籍,同时用户还能参与我们推荐的互动游戏,给广大的IT技术人士忙碌工作之余带来轻松休闲一刻。
微信扫一扫
关注Chinabyte

我要回帖

更多关于 拷贝构造函数何时调用 的文章

 

随机推荐