游戏开发之拷贝构造函数,即复制构造函数(explicit关键字及拷贝构造函数的调用时机)(C++基础)

拷贝构造函数是一个特殊的构造函数,是用一个类对象赋值给另外一个类对象时调用。
拷贝构造函数如果没有重写,编译器会自动生成。而重写了拷贝构造函数,编译器不会在生成默认拷贝构造函数,默认构造函数编译器也不会自动生成,需要程序员自己手写。
拷贝构造函数一般用于深拷贝(如果类的内部使用指针则需要重写)。
语法:类名(const 类名& 变量名){函数体}

C++类的构造函数按类型分类:分为普通构造函数拷贝构造函数(复制构造函数)

1.类的拷贝构造函数(复制构造函数)

 class A{public://拷贝构造函数  是一个特殊的构造函数/*拷贝构造函数如果没有重写,编译器会自动生成。而重写了拷贝构造函数,编译器不会在生成默认拷贝构造函数,默认构造函数编译器也不会自动生成,需要程序员自己手写。*///用一个类赋值给另外一个类时调用//一般用于深拷贝//如果类的内部使用指针则需要重写//语法:类名(const 类名& 变量名){函数体}int a;A(){std::cout << "调用默认构造函数" << std::endl;_age = 0;}//有参构造函数A(int age) {std::cout << "1个参数" << std::endl;_age = age;}A(const A &a_){std::cout << "调用拷贝构造函数" << std::endl;a = a_.a;_age = a_._age;}void Print() {std::cout << "Age:" << _age << std::endl;}private:int _age;};int main(){A a1;a1.a = 200;A a2(a1);//很像赋值,语义不明确,不推荐使用A a3 = a1;return 0;}

关于使用匿名对象调用拷贝构造函数:

class A{public:int a;A(){std::cout << "调用默认构造函数" << std::endl;_age = 0;}//有参构造函数A(int age) {std::cout << "1个参数" << std::endl;_age = age;}A(const A &a_){std::cout << "调用拷贝构造函数" << std::endl;a = a_.a;_age = a_._age;}void Print() {std::cout << "Age:" << _age << std::endl;}private:int _age;};int main(){//匿名对象:没有名字的对象。//匿名对象:显示调用构造函数A();//匿名对象调用a3实体的拷贝构造函数A a3 = A(300);a3.Print();//匿名对象调用a4实体的拷贝构造函数//注意:使用匿名对象初始化判断哪一个构造函数需要看匿名对象的参数类型A a4(A(400));a4.Print();//此时A(a6) 等价于 A a6A(a6);a6.Print();return 0;
}

b 为 A 的实例化对象, A a = A(b) 和 A(b)的区别?
当 A(b) 有实例化对象来接收的时候,那么编译器认为他是一个匿名对象;当没有变量来接的时候,编译器认为你A(b)就等价于A b。

TIPS:不能调用拷贝构造函数初始化匿名对象。
示例如下:

 class B {public:B() {std::cout << "默认构造函数!" << std::endl;}B(const B& teacher) {std::cout << "拷贝构造函数!" << std::endl;}public:int mAge;};int main(){B t1;B(t1);//错误,不能用拷贝构造函数初始化一个匿名函数!!return 0;}

2.explicit关键字

explicit用于修饰构造函数,防止隐式转化。
主要是针对单参数的构造函数(或者除了第一个参数外其余参数都有默认值的多参构造)而言。
限制在构造时使用:类对象实体 = 初始化,这种格式进行初始化。

 class A{public:explicit A(int a) { std::cout << "构造函数A" << std::endl; }//explict 明确语义,避免二义性A(const A &a_){std::cout << "调用拷贝构造函数" << std::endl;a = a_.a;}};class B{public:B(int a) { std::cout << "构造函数A" << std::endl; }};int main(int argc, char** argv){A a1 = 1; //错误,不允许隐式转换A a2(1);  //正确B b1 = 1; //正确B b2(2); //正确A a3;a3.a = 200;A a4(a3);//很像赋值,语义不明确,不推荐使用A a5 = a1;//错误。附加条件explicit,限制条件后,便不允许该种用法return 0;}

3.拷贝构造函数的调用时机

数据结构如下:

 class A{public:A(){std::cout << "默认构造函数!" << std::endl;_nAge = 10;}A(int age){std::cout << "有参构造函数!" << std::endl;_nAge = age;}A(const A& person){std::cout << "拷贝构造函数!" << std::endl;_nAge = person._nAge;}~A(){std::cout << "析构函数!" << std::endl;}private:int _nAge;};void test(A p) {}A test2(){A p(10);std::cout << "局部变量p:" << *(int*)&p << std::endl;return p;}void test3(){A p = test2();std::cout << "局部变量p:" << *(int *)&p << std::endl;}

1.旧对象初始化新对象会调用拷贝构造函数

int main()
{//1.旧对象初始化新对象A p(10);A p1(p);A P2 = A(p);//相当于A p2(A(p));A p3 = p;//相当于A p3(p);return 0;
}

2.函数的形参是普通类对象,实参也是普通的类对象,调用函数会调用拷贝构造函数

int main()
{//2.函数的形参是普通类对象,实参也是普通的类对象,调用函数会调用拷贝构造函数A p4(10);test(p4);return 0;
}

3.函数返回局部类对象会调用拷贝构造函数

int main()
{//3.函数返回局部类对象会调用拷贝构造函数test2();return 0;
}

4.函数调用返回局部类对象的函数并初始化另一个类对象

在vs2017的debug模式下,调用一次拷贝构造函数
在vs2017的release模式下,不调用拷贝构造函数

int main()
{//4.函数调用返回局部类对象的函数并初始化另一个类对象//在vs2017的debug模式下,调用一次拷贝构造函数//在vs2017的release模式下,不调用拷贝构造函数test3();return 0;
}


TIPS:test3()说明编译器在编译期间会对拷贝构造函数的调用进行优化。

游戏开发之拷贝构造函数,即复制构造函数(explicit关键字及拷贝构造函数的调用时机)(C++基础)相关推荐

  1. 构造函数和复制函数java_什么是Java构造函数?

    构造函数和复制函数java 在开放源代码,跨平台编程中,Java是(无可争议的)重量级人物. 尽管有许多很棒的 跨平台 框架 ,但很少有像Java这样统一和直接的框架 . 当然,Java还是一种非常复 ...

  2. 学习3D游戏开发进阶之路

    笔者从事IT行业15年了,一直奋斗在一线编程,从普通程序员逐步成长到上市公司技术总监,目前在创业公司担任技术合伙人,主要负责公司整个项目团队的技术管理.在网上或者论坛上很多同学请教过我关于如何学习3D ...

  3. 棋牌游戏开发会low吗 中国棋牌文化底蕴探究

    不知道大家是否有过这样一种念头:觉得棋牌游戏很low,赶不上"王者荣耀""吃鸡"等大型网游,现在的人哪会去玩棋牌游戏呢!摩天游棋牌游戏开发小编要告诉大家,这是一 ...

  4. unity超级马里奥2d游戏开发-03瓦片地图场景搭建

    大家好,我是小兵,今天给大家带来Untiy开发超级马里奥游戏的第3课,瓦片地图搭建,如果你想查看完整的教程,请访问我的个人博客geekape.net. 前两节课都没涉及具体的游戏制作,算是一个开胃菜, ...

  5. 游戏开发完整流程之美

    1. 立项 Ø 一个项目立项的原因可能性非常多,有可能是公司拿到一个好的IP,也有可能是几个负责人有个很棒的idea,亦或是老板的梦想是做一个XX类型的游戏,这边不做过多的讨论. Ø 立项过程中应该包 ...

  6. Unity手机游戏开发:从搭建到发布上线全流程实战

    前言: 技术书籍是学习技术知识的重要资源之一.读技术书可以帮助我们学习新技能和知识,技术书籍提供了可靠的.全面的信息,帮助我们快速学习新技能和知识.同时技术书籍有助于保持你的竞争力,因为它们提供了最新 ...

  7. C++拷贝构造函数(复制构造函数)详解

    link 复制构造函数是构造函数的一种,也称拷贝构造函数,它只有一个参数,参数类型是本类的引用. 如果类的设计者不写复制构造函数,编译器就会自动生成复制构造函数.大多数情况下,其作用是实现从源对象到目 ...

  8. 拷贝构造函数c语言,C++拷贝构造函数(复制构造函数)详解

    复制构造函数是构造函数的一种,也称拷贝构造函数,它只有一个参数,参数类型是本类的引用. 复制构造函数的参数可以是 const 引用,也可以是非 const 引用. 一般使用前者,这样既能以常量对象(初 ...

  9. [ C++ ] — 拷贝构造函数(复制构造函数)

    拷贝构造函数 拷贝构造函数就是用 同一类型的对象复制成员值来初始化对象(当出现类的 "=" 赋值时,就会调用拷贝构造函数) 简单来说,拷贝构造函数就是来复制对象的 默认拷贝构造函数 ...

  10. C++拷贝构造函数(复制构造函数)详解篇

    拷贝和复制是一个意思,对应的英文单词都是copy.对于计算机来说,拷贝是指用一份原有的.已经存在的数据创建出一份新的数据,最终的结果是多了一份相同的数据.例如,将 Word 文档拷贝到U盘去复印店打印 ...

最新文章

  1. 在B站如何不动一根手指,就可以养成6级大佬?
  2. HTML5--sessionStorage、localStorage、manifest
  3. CCF-CSP 201903-1 小中大(C++满分代码)
  4. Eclipse插件开发总结(第二天)
  5. C++学习之路—继承与派生(四)拓展与总结
  6. laravel5.5使用sendCloud邮件服务
  7. 4.RabbitMQ 4种交换模式
  8. BZOJ 4802 欧拉函数(Pollard_Rho)
  9. 风阻能发电装置叶片的动力学仿真
  10. Lucas-Kanade算法
  11. mysql 修改校对规则,整合MYSQL校对规则
  12. WCF服务系列——定义宿主(IIS服务宿主)
  13. 微信二次分享(标题、摘要、缩略图)
  14. 无法加载文件 XXX,因为在此系统上禁止运行脚本。有关详细信息,请参阅 https:/go.microsoft问题解决
  15. 七夕超多表情包入侵 - 100%提升博客美感(六千粉丝福利)!
  16. 【读书随记】周末充电,学习Java更轻松(文末送书)
  17. Java版本企业电子招投标采购系统源码——功能模块功能描述+数字化采购管理 采购招投标
  18. 【YOLO】YOLO简介
  19. 【全栈接口测试进阶系列教程】入门到入职的jmeter接口测试工具实战,接口测试步骤,正则表达式jsonpath,断言,接口加密,beanshell,jdbc,jmeter+ant+jenkins
  20. 极路由1S刷openwrt

热门文章

  1. 【每日算法Day 75】字节跳动面试题:手撕困难题,看过我Day 71的人都会做了!...
  2. numpy-np.Inf
  3. python接口自动化 post请求,body 带headers参数
  4. Java判断文件是否为图片
  5. 人类视觉计算理论经典著作,豆瓣评分9.7,中文版惊鸿面世
  6. 运营破局,四步完成从0到1
  7. 我所理解的Cocos2d-x
  8. 19【推荐系统3】AutoRec
  9. 8.8LSTM作为元学习器学习梯度下降
  10. 【SimpleITK】分割label覆盖到原图上显示