首页
学习
活动
专区
工具
TVP
发布
精选内容/技术社群/优惠产品,尽在小程序
立即前往

为什么转换运算符调用复制构造函数两次,而等效的函数只调用一次?

转换运算符调用复制构造函数两次的原因是为了确保在进行类型转换时,生成一个新的对象并将原始对象的值复制到新对象中。这样做的目的是为了避免对原始对象的修改,同时保留原始对象的值。

当使用转换运算符进行类型转换时,首先会调用复制构造函数创建一个临时对象,该临时对象的值与原始对象相同。然后,该临时对象会被传递给转换运算符进行类型转换操作。最后,转换运算符返回的结果是一个新的对象,该对象是通过复制构造函数从临时对象中创建的。

相比之下,等效的函数只调用一次复制构造函数是因为它们不涉及类型转换。这些函数只是执行一些操作,而不需要创建新的对象或进行类型转换。

需要注意的是,转换运算符调用复制构造函数两次可能会带来一些性能上的开销。因此,在设计和实现转换运算符时,需要权衡性能和功能需求,确保在不影响程序性能的前提下实现所需的类型转换功能。

腾讯云相关产品和产品介绍链接地址:

  • 腾讯云云服务器(CVM):提供弹性计算能力,满足各种业务需求。详情请参考:https://cloud.tencent.com/product/cvm
  • 腾讯云云数据库MySQL版:提供高性能、可扩展的MySQL数据库服务。详情请参考:https://cloud.tencent.com/product/cdb_mysql
  • 腾讯云云原生容器服务(TKE):提供高度可扩展的容器化应用管理平台。详情请参考:https://cloud.tencent.com/product/tke
  • 腾讯云人工智能平台(AI Lab):提供丰富的人工智能算法和工具,支持开发者构建智能化应用。详情请参考:https://cloud.tencent.com/product/ai
  • 腾讯云物联网套件(IoT Hub):提供一站式物联网解决方案,帮助开发者快速构建物联网应用。详情请参考:https://cloud.tencent.com/product/iothub
  • 腾讯云移动推送(TPNS):提供高效、稳定的移动消息推送服务,支持多种推送方式。详情请参考:https://cloud.tencent.com/product/tpns
  • 腾讯云对象存储(COS):提供安全、稳定、低成本的云存储服务,适用于各种数据存储需求。详情请参考:https://cloud.tencent.com/product/cos
  • 腾讯云区块链服务(BCS):提供一站式区块链解决方案,帮助企业快速搭建和部署区块链应用。详情请参考:https://cloud.tencent.com/product/bcs
页面内容是否对你有帮助?
有帮助
没帮助

相关·内容

C++基础-类和对象

声明构造函数时务必考虑使用关键字 explicit,以避免隐式转换。 务必将类成员声明为 std::string 和智能指针类(不是原始指针),因为它们实现了复制构造函数,可减少您工作量。...将 Copy() 返回值作实参,再次调用复制构造函数 return 0; } 上例中,参考注释,实例化 sayHelloAgain 对象时,复制构造函数调用两次。...如果对象很大,两次复制造成性能影响不容忽视。 为避免这种性能瓶颈, C++11 引入了移动构造函数。...增加移动构造函数后,上一示例中,将首先调用移动构造函数,然后调用复制构造函数复制构造函数只被会调用一次。 3. 析构函数 析构函数在对象销毁时被调用。执行去初始化操作。...为禁止赋值,可将赋值运算符声明为私有的。复制构造函数和赋值运算符声明为私有的即可,不需要实现。这样,如果代码中有对对象复制或赋值,将无法编译通过。

98020

当类构造与析构时候...

关于虚函数部分不在这篇再提,上一篇提过了。 文章目录 什么时候会调用默认构造函数 什么时候调用拷贝构造函数? 什么时候调用赋值运算符? 深拷贝与浅拷贝 成员初始化列表概念,为什么用它会快一些?...NRV优化,但是由于返回方式是值传递,所以会在返回值地方调用拷贝构造函数 ---- 什么时候调用赋值运算符?...赋值运算符是执行某种运算,将一个对象复制给另一个对象(已经存在)。调用是拷贝构造函数还是赋值运算符,主要是看是否有新对象实例产生。...---- 深拷贝与浅拷贝 浅复制 :只是拷贝了基本类型数据,引用类型数据,复制后也是会发生引用,我们把这种拷贝叫做“(浅复制)浅拷贝”,换句话说,浅复制仅仅是指向被复制内存地址,如果原地址中对象被改变了...用初始化列表会快一些原因是,对于类型,它少了一次调用构造函数过程,而在函数体中赋值则会多一次调用。而对于内置数据类型则没有差别。

63920
  • 【C++】类和对象(中)

    构造函数是一个特殊成员函数,名字与类名相同,创建类类型对象时由编译器自动调用,保证每个数据成员都有 一个合适初始值,并且在对象生命周期内只调用一次 特性 构造函数是特殊成员函数,需要注意是,...return 0; } 除此之外,如下代码会造成二义性:(无参构造函数和全缺省构造函数都称为默认构造函数,并且默认构造函数只能有一个。...拷贝构造函数数只有一个且必须使用引用传参,使用传值方式会引发无穷递归调用。...Func1(d1); Func2(d1); return 0; } 注意:如果我们没写拷贝构造函数,编译器会自动生成默认拷贝构造函数,内置类型是按照字节方式直接拷贝自定义类型是调用其拷贝构造函数完成拷贝...对于赋值重载(复制拷贝)和拷贝构造区别: 赋值重载(复制拷贝) 已经存在两个对象之间拷贝 拷贝构造(初始化) 一个初始化另一个马上要创建对象 赋值运算符主要有五点: 参数类型(如上const

    1.2K30

    C++ explicit关键字详解

    = 10;” 这句为什么是可以呢?...在C++中, 如果构造函数只有一个参数时, 那么在编译时候就会有一个缺省转换操作:将该构造函数对应数据类型数据转换为该类对象....// 这样也是不行, 因为取消了隐式转换, 除非类实现操作符"="重载 explicit关键字作用就是防止类构造函数隐式自动转换....上面也已经说过了, explicit关键字只对有一个参数构造函数有效, 如果类构造函数参数大于或等于两个时, 是不会产生隐式转换,所以explicit关键字也就无效了...., explicit关键字依然有效, 此时, 当调用构造函数时只传入一个参数, 等效于只有一个参数构造函数, 例子如下: class CxString // 使用关键字explicit声明

    7.9K40

    C++避坑指南

    /a.out x = 2y = 1 如果我们需要指定依赖关系,比如y依赖x进行初始化,可以利用这样一个特性来实现:函数内部静态对象在函数一次调用时初始化,且只被初始化一次。...3.1 隐式转换 C++自定义类型在以下两种情况会发生隐式转换: 1) 类构造函数只有一个参数或除第一个参数外其他参数有默认值; 2) 类实现了operator type()函数;...上述String类存在到const char *隐式转换,strcat函数返回时String隐身转换成const char *,String对象已经被销毁,返回const char *指向无效内存区域...这也是std::string不提提供const char *隐式转换专门提供了c_str()函数显示转换原因。...shared_ptr sp(new Object());  这条语句会调用两次内存管理器,一次用于创建Object对象,一次用于创建控制块。

    1.6K30

    类与对象中篇

    构造函数是一个特殊成员函数,名字与类名相同,创建类类型对象时由编译器自动调用,以保证每一个成员变量都有一个合适初始值,并且在对象整个生命周期内只调用一次。...,为什么最后会调用Time类析构函数?...但是:main函数 // 中不能直接调用Time类析构函数,实际要释放是Date类对象,所以编译器会调用Date类析构 // 数,Date没有显式提供,则编译器会给Date类生成一个默认析构函数...拷贝构造函数特征: 1.拷贝构造函数构造函数一个重载形式。 2.拷贝构造函数数只有一个且必须是类类型对象引用,使用传值方式编译器直接报错,因为会引发无穷递归调用。...注意:赋值运算符重载和拷贝构造区别: 拷贝构造是用一个同类型对象去初始化另一个对象,赋值运算符重载是两个对象已经存在,此时要将一个对象复制拷贝给另一个对象。

    52430

    C++11 lambda

    lambda和functor函数调用执行代码是相同。唯一区别是lambda构造函数被内联到创建lambda函数中,不是像构造函数那样是一个单独函数。...与按值捕获一样,functor和lambda调用代码是等价,但是lambda构造函数是内联functor则不是。 结论 C ++ lambda和子比相似之处更多。...总结主要区别: 1、子和lambda总是传递一个this指针,普通函数自然不是。这会消耗一个额外寄存器和8个字节堆栈空间。 Lambda“构造函数”被内联到创建Lambda函数中。...这显着减少了执行复制量(lambda2条指令,5条指令),以及避免了函数调用建立和拆卸。...在大多数情况下,“漏斗式”普通函数已经完全可以满足需要了,但在某些特殊情况下,下一次函数执行是在上一次函数执行结果基础上进行。这时,函数就需要记住上一次执行状态数据以备下一次函数执行使用。

    1.1K30

    C++学习知识点

    : 主要是性能问题,对于内置类型,如int, float等,使用初始化类表和在构造函数体内初始化差别不是很大,但是对于类类型来说,最好使用初始化列表,使用初始化列表少了一次调用成员默认构造函数过程...为什么函数形参多是const修饰引用 使用引用是防止值传递,值传递之前会将实参在堆栈产生一份拷贝,引用则不会,因此引用传递会改变实参值。...(2) 当函数参数为类对象时,这时调用函数时使用是值传递,也会产生对象复制。...(3) 函数返回值是类对象时,在函数调用结束时,需要将函数对象复制一个临时对象并传给改函数调用处。 12....对于类定义对象什么时候用new,什么时候不用new认识 (1) 构造函数只适用于类成员初始化,与分配类对象空间无关; (2) 隐式执行默认构造函数,初始化申明在栈上类对象,直接申明,不要使用

    1.7K20

    C++之类和对象

    默认构造 构造函数第七个特性是:无参构造函数和全缺省构造函数都称之为默认构造函数,并且默认构造函数只能有一个。...拷贝构造 基础知识 复制是我们经常使用到操作,如果想复制一个类的话该怎么办?C++对于这个问题解决方案是提供了一种叫做拷贝构造成员函数。...拷贝构造也是特殊成员函数,其特征如下: 1.拷贝构造函数构造函数一个重载形式,当我们使用拷贝构造实例化对象时,编译器不再调用构造函数; 2.拷贝构造函数数只有一个且必须是类类型对象引用,...; 引用做参数 拷贝构造第二个特性说拷贝构造函数参数必须是引用,否则会有无穷递归现象产生,这是因为传值传参本身就是一次拷贝(传值传参是建立一个临时变量,然后将值拷贝给这个临时变量),拷贝类就需要调用拷贝构造...,连续构造+拷贝构造->优化为直接构造 ** 可以看到这里只调用一次构造函数,但是根据前面说隐式类型转换我们可以知道中间有个临时变量产生,需要先构造这个临时变量,再将这个临时变量拷贝构造aa,但编译器经过优化以后直接成了将

    1.2K00

    对象传值与返回

    在32处理器上,push指令一次只能压入4个字节数据,那么对于long long就需要两次压栈指令了,double类型参数就需要sub esp,8结合mov指令完成参数进栈操作。...为此,我们定义一个简单类A,为了防止编译器对我们代码优化处理(参考我前一篇博文),我们自己定义构造函数复制构造函数和赋值运算符重载函数。...由于对象是值传递方式,因此,对象传递之前需要进行一次对象拷贝(从原对象到实参)。函数调用结束后还需要将返回值对象进行一次拷贝。我们看看VS2010处理方式。 ?...参数正是刚才fun调用结束后eax值,因为它存储了返回值对象地址。ecx记录this指针,正是被赋值对象地址(a地址)。赋值运算符重载函数调用结束后,完成返回值对象赋值操作。...对象返回时,也需要将函数处理结果进行一次对象拷贝,不过被拷贝返回值对象内存已经在函数调用之前已经开辟出来了,函数只需要记录它地址即可,然后调用拷贝构造函数初始化它。 3.

    2.5K80

    【C++修炼之路】3. 类和对象(中)

    为什么最后会调用Time类析构函数?...拷贝构造函数数只有一个且必须是类类型对象引用,使用传值方式编译器直接报错,因为会引发无穷递归调用 为什么传值会无穷递归呢?...),发现在调用Func1时同时也调用了拷贝构造函数Func2却没有。...: 通过这个逻辑不难发现,每一次调用这个拷贝构造函数之后都会将传值拷贝到拷贝构造函数参数,而这个过程又会进入到下一层拷贝构造函数,就这样永无止境。...但在这里,我们还需要思考一些问题: 传值传参是一次拷贝构造,传返回值也是一次拷贝构造,因此为了提升性能我们采用传引用返回。那么为什么返回*this能传引用呢?

    50900

    类和对象之六大基础函数

    构造函数是一个特殊成员函数,名字与类名相同,创建类类型对象时由编译器自动调用,以保证 每个数据成员都有 一个合适初始值,并且在对象整个生命周期(类作用域)内只调用一次。...可能是考虑到向前兼容吧,反正大佬世界我也不懂 doge)。 7. 无参构造函数和全缺省构造函数都称为默认构造函数,并且默认构造函数只能有一个。...拷贝构造函数数只有一个且必须是“类”类型对象引用,使用传值方式编译器直接报错,因为会引发无穷递归调用(为啥看下文)。...,为什么最后会调用Time类析构函数?...但是: //main函数 // 中不能直接调用Time类析构函数,实际要释放是Date类对象,所以编译器会调用Date //类析构 // 数,Date没有显式提供,则编译器会给Date类生成一个默认析构函数

    56520

    C++10中移动语义

    ,其实会调用两次拷贝构造函数。...第一次默认拷贝构造函数调用是在demo对象初始化过程中; 两次拷贝构造函数实在clone函数调用过程中: clone函数中利用this对象初始化demo对象进行一个拷贝构造,然后返回demo...返回过程中会再次调用一次拷贝构造返回局部对象demo一个拷贝。...对象移动语义(Move Semantics)需要实现移动构造函数(move constructor)和移动赋值运算符(move assignment operator)。...如果源对象是在复制或者赋值结束以后被销毁临时对象,编译器会使用两种方法。移动构造函数和移动赋值运算符将成员变量从源对象复制/移动到新对象,然后将源对象变量设置为空值。

    49830

    C#关键字常见面试题

    静态构造函数只调用一次,在程序所驻留应用程序域生存期内,静态类会保留在内存中(即使用Static修饰类,应用一旦启用静态类就会保留在内存中)。 静态类只包含静态成员 不能包含实例构造函数。...静态类不能包含实例构造函数。但是,它们可以包含静态构造函数。 静态成员和非静态成员区别? 成员主要指的是:字段、方法、属性、运算符、事件和构造函数等。...this 关键字表示当前对象引用,可以用于访问当前对象成员。它可以用来区分局部变量和实例变量、在构造函数调用其他构造函数、传递当前对象给其他方法等。 base 关键字有什么作用?...as运算符将表达式结果显式转换为给定引用类型或可以为null值类型。如果无法进行转换,则as运算符返回 null。...总结:as模式效率要比is模式高,因为借助is进行类型转换化,需要执行两次类型兼容检查。as只需要做一次类型兼容,一次null检查,null检查要比类型兼容检查快。 null是什么类型?

    16710

    C++11——对象移动与右值引用

    vector是一个常用容器了,我们可以很容易分析这这两次拷贝构造时机: (1)第一次是在函数foo中通过临时Obj对象Obj()构造一个Obj对象并入vector中; (2)第二次是通过从函数...左值到右值引用转换: 虽然不能直接将右值引用直接,但是我们可以显示地将一个左值转换为对应右值引用类型。我们可以通过调用新标准库中模板函数move来获得绑定到左值右值引用。...为了让我们自己定义类型支持移动操作,我们需要为其定义移动构造函数和移动赋值运算符。这两个成员类似对应拷贝操作,即拷贝构造和赋值运算符,但它们从给定对象窃取资源不是拷贝资源。...完成资源移动后,原对象不再保留资源,但移动构造函数还必须确保原对象处于可销毁状态。 移动构造函数相对于拷贝构造函数优点:移动构造函数不会因拷贝资源分配内存,仅仅接管源对象资源,提高了效率。...v时,又发生了一次元素拷贝,结果出现了无谓两次元素拷贝,这严重降低了程序性能。

    85920

    c++标准模板库

    c_str   我们发现fopen函数只支持const char*类型(即C语言格式字符串)数据,此时就可以用c_str来转换。   ...这个时候我们就发现问题了,s1和s2在类里面定义指针都指向了同一块空间,当程序结束时,s2析构函数释放空间,s1空间又释放了一次空间,一块空间被释放了两次,造成了程序崩溃。   ...s2 = "world"; //调用构造函数 String s3(s1); //调用拷贝构造函数 String s4 = s1; //调用拷贝构造函数...String s5; //调用构造函数 s5 = s1; //调用拷贝赋值运算符 return 0;...这是C++标准库里swap()函数   我们看到,标准库里方法要进行三次拷贝构造,且都是深拷贝。   string类里swap()函数只是简单进行值交换,所以效率更高。

    52410

    类与对象(中)

    默认成员函数:用户没有显式实现,编译器会生成成员函数称为默认成员函数。 初始化和清理以及拷贝复制是最重要。 析构函数不是在销毁对象,而是在清理空间。 2....函数名与类名相同。 2. 无返回值。(也不需要写void) 3. 对象实例化时编译器自动调用对应构造函数。 4. 构造函数可以重载。(这里重载指的是函数重载) 为什么构造函数支持函数重载?...d1是函数名,参数列表是空,返回值是Date。 7. 无参构造函数和全缺省构造函数都称为默认构造函数,并且默认构造函数只能有一个。...4.2 特征 拷贝构造函数也是特殊成员函数,其特征如下: 1.拷贝构造函数构造函数一个重载形式。 2.拷贝构造函数数只有一个且必须是类类型对象引用。...1.内置类型成员会完成浅拷贝/值拷贝 2.自定义成员会调用拷贝构造 注意:在编译器生成默认拷贝构造函数中,内置类型是按照字节方式直接拷贝自定义类型是调用其拷贝构造函数完成拷贝

    5110

    从基础入门到学穿C++(类和对象篇)【超详细】【一站式速通】

    如果每个对象都放成员函数,而这些成员函数却是一样,浪费空间 ps:explicit关键字:用explicit修饰构造函数,将会禁止构造函数隐式转换。...无参构造函数和全缺省构造函数都称为默认构造函数,并且默认构造函数只能有一个。 注意:默认构造函数:不传参就可以进行调用。...拷贝构造函数数只有一个且必须是类类型对象引用,使用传值方式编译器直接报错,因为会引发无穷递归调用。...我们在调用Func函数时候,实参d1传值给了d,这里发生了拷贝构造,利用d1构造出了d。 运算符重载 自定义类型是不能用运算符,要用就得实现运算符重载。..._day; } 运算符重载是为了让自定义类型可以像内置类型一样去使用运算符。 拷贝构造是在对象创建时候用另一个对象去初始化它,赋值运算符重载是为了实现两个都已经初始化好对象之间进行赋值。

    9010

    CC++学习之路(一)

    =右边本类对象复制给等号左边对象,它不属于构造函数,等号左右两边对象必须已经被创建         // 若没有显示写=运算符重载,则系统也会创建一个默认=运算符重载,只做一些基本拷贝工作...        //    调用类型转换构造函数         //    系统首先调用类型转换构造函数,将5.2创建为一个本类临时对象,然后调用等号运算符重载,将该临时对象赋值给c1        ...a[4]是类数组,有4个对象,调用构造函数4次,*p[5]是指针数组,也就是5个元素存放是指向MyClass类型对象指针,没有初始化指针为空,不指向任何对象,也不调用构造函数。        ...为什么?          MyClass a:定义一个对象,调用1次构造函数。          b[2]:定义含有两个元素数组,实际上定义两个对象,所以调用2次构造函数。         ...普通对象调用一次,对象数组调用N次(该数组含有N个元素)。只定义指针不给指针赋值,则不涉及内存分配,不调用构造函数

    80031

    【笔记】《C++Primer》—— 第三部分:类设计者工具

    构造函数来类型转换,则拷贝初始化还是直接初始化就无关紧要了 析构函数行为与构造函数相反,会自动销毁掉非static成员和调用成员析构 析构函数没有参数列表,所以成员销毁时行为完全依赖于成员自己 析构会在变量离开作用域或母构件销毁时销毁...我们一样可以自定义所需类型转换运算符,方法是一个没有返回类型也没有形参必须定义为成员函数operator type() const函数 尽管编译器对一个对象一次只进行一次自定义类型转换,但这个转换还可以放在一次内置转换之前或之后...,也就是对象最多可能隐式发生两次转换,这就容易导致二义性问题 如果调用重载时我们需要显式写出转换或用强制类型转换,则常常说明我们设计有不足 类型转换中有一个转换比较特别,那就是bool类型转换。...如果表达式不是引用也不是指针,则其动态类型永远与静态类型一致 派生类可以往基类类型转换基类不能隐式反向转换 一个派生类函数如果想要覆盖继承来函数,那必须名称和形参都一致,否则编译器会认为这两个函数是独立...,写法和15.6中指明重载基类函数一样,效果与定义一个空构造函数然后列表中调用基类构造函数一致 和普通函数using不同,对构造函数using不会改变构造函数访问级别 当基类构造函数中有默认实参时

    1.7K10
    领券