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

第 14 章 重载运算与类型转换

一个类中往往会同时定义这两种运算符,通常情况下,箭头运算符可以不执行任何操作,而是调用引用运算符并返回解引用结果元素地址。 重载箭头运算符必须返回类指针或者自定义了箭头运算符某个类对象。...一般情况下,比较两个无关指针将产生未定义行为,然而如果希望比较指针内存地址来 sort指针 vector,可以使用一个标准库函数对象来实现该目的。...vector nameTable; // 错误,nameTable中指针彼此之间没有联系,所以 <将产生未定义行为 sort(nameTable.begin(), nameTable.end...A()); A a = f(A(b)); 如果在同一个类中定义了多个转换源(或转换目标)是算术类型转换时,也产生二义性问题。...而如果使用命名函数来调用时,成员函数和非成员函数不会彼此重载。如果我们一个类既提供了转换目标是算术类型类型转换,也提供了重载运算符,则将会遇到重载运算符与内置运算符二义性问题。

87460

由浅入深理解面向对象思想组成模块

但是,需要注意是,如果我们不在无参构造函数中初始化成员变量,那么这些变量初始值将是未定义,这可能导致程序出错。...拷贝构造函数参数只有一个且必须是类类型对象引用,使用传值方式编译器直接报错,因为引发无穷递归调用。...若未显式定义拷⻉构造,编译器⽣成⾃动⽣成拷⻉构造函数。⾃动⽣成拷⻉构造对内置类型成员变量完成值拷⻉/浅拷⻉(⼀个字节⼀个字节拷⻉),⾃定义类型成员变量会调⽤他拷⻉构造(深拷贝)。...为什么拷贝构造函数参数一定要以引用形式? // 错误写法 Date(const Date d) { _year = d._year; _month = d....友元函数没有this指针 // 流提取运算符重载 ostream& operator<<(ostream& out, const Date& d) { out << d.

6810
您找到你想要的搜索结果了吗?
是的
没有找到

《Effective C++》读书笔记(二):构造析构赋值运算(条款05~条款12)

p = s;//error,报错显示operator是已删除函数 return 0; } 赋值不成功理由很简单,引用指向是不可以被改变,赋值的话就说明要改变引用指向对象。...同样const成员函数也是一样不能被改变!这种情况就必须自己定义一个赋值重载函数。...,只要把基类拷贝构造函数和赋值重载私有或者删掉,派生类就不可能默认生成拷贝构造和函数重载出来!...这样做好处是,如果有人在类中调用了这些被私有化函数,或者使用友元,那么会在连接期出现错误,而并非编译期错误。如果是发生在连接期错误,这种错误很难侦测出来!...6.条款10:令operator=返回一个reference to *this 也就是让赋值重载函数返回值是一个引用返回,这样是为了可以实现连锁赋值。

34710

关于C++中操作符重载疑问 :四个运算符=, ->, [], ()不可以重载为全局函数(友员函数)

: Call A operator=(int xx) 说明在类A中已经有相应赋值运算符重载函数时候,执行赋值语句a = 7;程序会去调用类A中相应赋值运算符重载函数,而不会像上面原来那样去调用有参构造函数...在此,我们可以对C++规则做出以下判断:   当类中没有定义赋值运算符重载成员函数时(注意,在未定义形参数据类型为该类类型赋值运算符重载函数时,编译器自动生成加入),当程序执行到某一赋值语 句时,...那么当把赋值运算符重载为类友员函数,在程序中执行类对象赋值语句时,程序就会出现两种矛盾选择。 1、因为它认为类中并没有重载赋值运算符成员函数,所以它根据C++规则,会去调用相应构造函数。...程序是不允许有矛盾不确定选择,所以当赋值运算符重载为类友元函数时,编译器就会提示错误。 对于剩下3个运算符 ->, [], () 为什么不能重载为友元函数,也是跟上面一样道理。...A友元函数时,程序就会出现跟把赋值运算符重载友元一样情况,即产生矛盾性。

98420

C++ 运算符重载

有了+重载,编译器就将a+b理解为运算符函数调用,即operator+(a,b),因此第 21 行就等价于:  c = operator+(a, b);  即以两个操作数 a、b 作为参数调用名为...在 a、b、c 都是 String 对象时,(a=b)=c;等价于  ( a.operator=(b) ).operator=(c);  a.operator=(b) 返回 a 引用后,通过该引用继续调用...此外,s1 和 s2 消亡时都会执行delete[] str;,这就使得同一片存储空间被释放两次,导致严重内存错误,可能引发程序意外中止。...在本程序中,执行第 34 行cout<<c进入 operator<< 后,os 引用就是 cout,因此第 34 行就能产生输出。...经过适当重载后,(类型名)对象这个对对象进行强制类型转换表达式就等价于对象.operator 类型名(),即变成对运算符函数调用。 下面的程序 double 类型强制转换运算符进行了重载

1.2K00

C++查缺补漏

调用用默认构造函数(即无形参)初始化 处理完初始化列表之后,再执行构造函数函数体 前向引用声明 如果需要在某个类声明之前,引用该类,则应进行前向引用声明 前向引用声明只为程序引入一个标识符,但具体声明在其他地方...(从左向右) 初始化列表中成员进行初始化 顺序按照它们在类中定义顺序 对象成员初始化时自动调用其所属类构造函数,由初始化列表提供参数 执行派生类构造函数体中内容 派生类复制构造函数 派生类未定义复制构造函数情况...析构函数不被继承,派生类如果需要,要自行声明析构函数 声明方法与无继承关系时类析构函数相同 不需要显式地调用基类析构函数,系统自动隐式调用 先执行派生类析构函数函数体,再调用基类析构函数 访问从基类继承成员...,则在访问此共同基类中成员时,将产生冗余,并有可能因冗余带来不一致性 虚基类声明 以virtual说明基类继承方式 例:class B1:virtual public B 作用 主要用来解决多继承时可能发生同一基类继承多次而产生二义性问题...- 在虚函数显式重载中运用,编译器检查基类是否存在一虚拟函数,与派生类中带有声明override虚拟函数,有相同函数签名(signature);若不存在,则会回报错误 多态行为基础:基类声明虚函数

2.5K10

【C++修炼之路】4. 类和对象(中):日期类实现

(上面的const修饰引用返回,虽然没警告,但是不代表没错误) static一般有两个作用,规定作用域和存储方式(静态存储)。...{} 但实际上,我们采用运算符重载,就是让代码可读性更高,让其可以像普通内置类型一样加减,而不是调用函数,调用函数也就是失去了运算符重载意义。...因此,这样才是解决此问题最终方案。需要注意是友元函数不易声明过多,因为这样造成耦合度过高导致程序不易观察。 2.3 流总结 上面的一共讨论了两个问题并得到了合理解决。...(仍以Date类) 对于Date类,当我们将其const之后,用Print方法却显示错误。事实上,这个提示已经很清楚了,是因为调用产生了权限放大。...而对于上述我们所定义d2,就是this指向内容,也就是说,不可修改d2传到Print中变成了可修改类型,这就是权限放大,因此这样产生错误

78700

漫谈C++:良好编程习惯与编程要点

但是为了一致,不妨统一使用引用。 ⑥ 如果可以,函数返回值也尽量使用引用引用方式返回函数局部变量引发程序未定义行为,离开函数作用域局部变量被销毁,引用该变量没有意义。...而在函数被调用时才创建出来对象,一定不能返回引用。 说回operator +=,其返回值就是引用,原因在于,执行a+=b时,a已经在内存上存在了。...而operator + ,其返回值不能是引用,因为a+b值,在调用operator +时候才产生。...imag(x)+ imag(y)); } 在operator +=中返回引用还是必要,这样可以使用连续操作: c3 += c2 += c1; ⑦ 如果重载了操作符,就考虑是否需要多个重载 就我们复数类来说...当企图rhs内存进行访问是,结果是未定义。 static与类 ① 不和对象直接相关数据,声明为static 想象有一个银行账户类,每个人都可以开银行账户。

45630

C++ 运算符重载

有了+重载,编译器就将a+b理解为运算符函数调用,即operator+(a,b),因此第 21 行就等价于:  c = operator+(a, b);  即以两个操作数 a、b 作为参数调用名为...在 a、b、c 都是 String 对象时,(a=b)=c;等价于  ( a.operator=(b) ).operator=(c);  a.operator=(b) 返回 a 引用后,通过该引用继续调用...此外,s1 和 s2 消亡时都会执行delete[] str;,这就使得同一片存储空间被释放两次,导致严重内存错误,可能引发程序意外中止。...在本程序中,执行第 34 行cout<<c进入 operator<< 后,os 引用就是 cout,因此第 34 行就能产生输出。...经过适当重载后,(类型名)对象这个对对象进行强制类型转换表达式就等价于对象.operator 类型名(),即变成对运算符函数调用。 下面的程序 double 类型强制转换运算符进行了重载

1.1K20

漫谈C++:良好编程习惯与编程要点

内置类型值传递与引用传递效率没有多大差别,甚至值传递效率更高。例如,传递char类型时,值传递只需传递一个字节;引用实际上是指针实现,需要四个字节(32位机)传递开销。...但是为了一致,不妨统一使用引用。 ⑥ 如果可以,函数返回值也尽量使用引用引用方式返回函数局部变量引发程序未定义行为,离开函数作用域局部变量被销毁,引用该变量没有意义。...而在函数被调用时才创建出来对象,一定不能返回引用。 说回operator +=,其返回值就是引用,原因在于,执行a+=b时,a已经在内存上存在了。...而operator + ,其返回值不能是引用,因为a+b值,在调用operator +时候才产生。...当企图rhs内存进行访问是,结果是未定义。 ? static与类 ① 不和对象直接相关数据,声明为static 想象有一个银行账户类,每个人都可以开银行账户。

55770

漫谈 C++:良好编程习惯与编程要点

但是为了一致,不妨统一使用引用。 ⑥ 如果可以,函数返回值也尽量使用引用引用方式返回函数局部变量引发程序未定义行为,离开函数作用域局部变量被销毁,引用该变量没有意义。...而在函数被调用时才创建出来对象,一定不能返回引用。 说回operator +=,其返回值就是引用,原因在于,执行a+=b时,a已经在内存上存在了。...而operator + ,其返回值不能是引用,因为a+b值,在调用operator +时候才产生。...imag(x)+ imag(y)); } 在operator +=中返回引用还是必要,这样可以使用连续操作: c3 += c2 += c1; ⑦ 如果重载了操作符,就考虑是否需要多个重载 就我们复数类来说...当企图rhs内存进行访问是,结果是未定义。 static与类 ① 不和对象直接相关数据,声明为static 想象有一个银行账户类,每个人都可以开银行账户。

18530

漫谈 C++:良好编程习惯与编程要点

但是为了一致,不妨统一使用引用。 ⑥ 如果可以,函数返回值也尽量使用引用引用方式返回函数局部变量引发程序未定义行为,离开函数作用域局部变量被销毁,引用该变量没有意义。...而在函数被调用时才创建出来对象,一定不能返回引用。 说回operator +=,其返回值就是引用,原因在于,执行a+=b时,a已经在内存上存在了。...而operator + ,其返回值不能是引用,因为a+b值,在调用operator +时候才产生。...imag(x)+ imag(y)); } 在operator +=中返回引用还是必要,这样可以使用连续操作: c3 += c2 += c1; ⑦ 如果重载了操作符,就考虑是否需要多个重载 就我们复数类来说...当企图rhs内存进行访问是,结果是未定义。 static与类 ① 不和对象直接相关数据,声明为static 想象有一个银行账户类,每个人都可以开银行账户。

16520

C++ 编程习惯与编程要点

内置类型值传递与引用传递效率没有多大差别,甚至值传递效率更高。例如,传递char类型时,值传递只需传递一个字节;引用实际上是指针实现,需要四个字节(32位机)传递开销。...但是为了一致,不妨统一使用引用。 ⑥ 如果可以,函数返回值也尽量使用引用引用方式返回函数局部变量引发程序未定义行为,离开函数作用域局部变量被销毁,引用该变量没有意义。...而在函数被调用时才创建出来对象,一定不能返回引用。 说回operator +=,其返回值就是引用,原因在于,执行a+=b时,a已经在内存上存在了。...而operator + ,其返回值不能是引用,因为a+b值,在调用operator +时候才产生。...当企图rhs内存进行访问是,结果是未定义。 static与类 ① 不和对象直接相关数据,声明为static 想象有一个银行账户类,每个人都可以开银行账户。

1.1K30

【笔记】《C++Primer》—— 第14章:重载运算和类型转换

这一章介绍了运算符重载和类型转换,其中最重要各种运算符运用,14.8function类运用和14.9类型转换时可能产生二义性理解,其余内容不多,这篇看起来很多节但其实只是因为内容比较散而已...14.1 基本概念 运算符重载在13章中提到过一点点,重载运算符实际上是具有特殊名字能被特殊调用函数 重载运算符名字由 operator运算符 组成,和普通函数一样,重载运算符函数也需要自己返回值...,参数们都会被以未定义顺序求值 尽管我们可以重载大多数运算符,但是对于逗号运算符,取地址运算符和逻辑运算符我们一般不去重载它因为容易起误会 我们应只在操作含义清晰明了时才重载运算符,且有些运算符我们最好还限定其成员性...function中,因为产生二义性,解决方法是使用函数指针处理 14.9 重载,类型转换与运算符 我们一样可以自定义所需类型转换运算符,方法是一个没有返回类型也没有形参必须定义为成员函数...如果我们想要解决二义性可以显式写出转换函数来表明路径,注意我们无法用强制类型转换解决因为同样产生二义性 当某个类提供了多个向内置类型转换时,可能触发第二点所说先转换为内置类型再发生内置转换,这也是二义性

64310

const 使用总结

当绑定到const对象时,我们称之为常量引用:const int ci = 1024;const int &cr = ci;cr = 0;// 错误,任何想通过cr改变引用对象值都不允许cosnt...// 错误丢失*cpconst限制使用auto自动类型推导时,auto忽略掉顶层const,而底层const则会保留下来:int i = 0;const int ci = i;const int...另外对于非const版本引用参数,意味着在函数内部可以也可能修改调用实参,这有时候不是你想要。...'a';上面的代码中,成员函数operator[]虽然定义为const,但却返回一个引用,从而允许返回结果进行赋值,这就违背了常量本意,造成后果是未定义行为。...,我们通过成员函数是否有const来进行重载,这样,常量对象只能调用常量成员函数,非常量对象既可以调用常量成员函数也可以调用非常量成员函数,但是对于非常量成员函数更加匹配,所以会调用非常量成员函数,我们可以定义两个重载函数

8910

适合具备 C 语言基础 C++ 入门教程(四)

+p这条输出信息同样也是因为执行了 ++p;而调用构造函数,那紧接着两条输出信息是如何产生呢,我们回过头去看看++p函数,可以看到 ++p函数是一个返回值为 Point类型函数,而上述中输出语句...上述详细地分析了各个打印信息输出原因,通过上述打印信息我们可以清楚知道程序在什么地方调用了构造函数,在什么地方调用了析构函数,再次回顾上述函数调用过程,可以看出来其实调用Point(const...,节省了程序运行空间,那如果将后++重载函数设置为引用可不可行呢,很显然,如果返回是 n引用,那么这在语法中就是错误,因为n是局部变量,局部变量在函数调用结束就销毁了,是不能作为引用对象。...最后,总结一下,对于一个函数来说,函数返回结果如果作为值返回,那么代码执行效率较低;如果作为引用返回,那么代码执行效率较高,但是会存在一个问题,引用返回可能导致函数运行出错,所以,在保证函数运行没有错误前提下...链接:https://pan.baidu.com/s/1BC55_QH-iV23-ON0v1OGSA 提取码:iyf7 如果您觉得我文章您有所帮助,欢迎关注我个人公众号:wenzi嵌入式软件

27630

【C++修行之道】类和对象(五)日期类实现、const成员、取地址及const和取地址操作符重载

GetMonthDay 函数可能预计会被频繁调用,这对于小型、频繁调用函数特别有益,可以提高程序执行效率。...语义上:后置运算符语义是先返回操作后对象,然后对对象进行递作。后置运算符关键在于返回操作前状态。 安全性:返回拷贝还避免了潜在外部修改,此时得到是一个独立值,而不是原始数据直接引用。..._day << "日" << endl; // 返回输出流引用,以便支持链式调用 return out; } // 重载输入流操作符>>,用于从输入流中读取数据并设置到Date对象中 istream...将 operator<< 参数顺序反过来导致函数不能正常作为流插入运算符使用,破坏标准库调用方式和使用习惯。...但这种做法是不推荐,因为它破坏了const正确性和对象常量性质,可能导致未定义行为或程序错误。通常来说,应该尽量避免这种做法。

8510

《C++Primer》第十四章 重载运算与类型转换

在执行输入运算符时可能发生下列错误: 当流含有错误类型数据时读取操作可能失败,例如输入运算符假定接下来读入是两个数字数据,但是输入不是数字数据,则读取数据及后续对流其他使用都将失败 当读取操作到达文件末尾或者遇到输入流其他错误时也失败...当一个lambda表达式通过引用捕获变量时,将由程序负责确保lambda执行时引用对象却是存在,因此编译器可以直接使用该引用而无需在lambda产生类中将其存储为数据成员。...则该代码在编译器看来将是合法 这段程序试图将输出运算符作用于输入流,因为istream本身并没有定义<<,所以本来这段代码应该产生错误。..., s2; SmallInt s3 = s1 + s2; // 使用重载operator int i = s3 + 0; // 二义性错误:既可以把0转换成SmallInt,然后使用SmallInt...+;也可以将s3转换成int,int执行内置加法运算 如果我们同一个类既提供了转换目标是算术类型类型转换,也提供了重载运算符,则将会遇到重载运算符与内置运算符二义性问题。

90410

适合具备 C 语言基础 C++ 教程(四)

++p;而调用构造函数,那紧接着两条输出信息是如何产生呢,我们回过头去看看++p函数,可以看到 ++p函数是一个返回值为 Point类型函数,而上述中输出语句 Point(const Point...上述详细地分析了各个打印信息输出原因,通过上述打印信息我们可以清楚知道程序在什么地方调用了构造函数,在什么地方调用了析构函数,再次回顾上述函数调用过程,可以看出来其实调用Point(const...M4QzImA1uYxnBK9 可以看到上述结果中,之前在 ++p后输出两条信息现在因为将返回值设置为引用之后就消失了,说明这样方法避免了调用构造函数和析构函数,节省了程序运行空间,那如果将后++...重载函数设置为引用可不可行呢,很显然,如果返回是 n引用,那么这在语法中就是错误,因为n是局部变量,局部变量在函数调用结束就销毁了,是不能作为引用对象。...最后,总结一下,对于一个函数来说,函数返回结果如果作为值返回,那么代码执行效率较低;如果作为引用返回,那么代码执行效率较高,但是会存在一个问题,引用返回可能导致函数运行出错,所以,在保证函数运行没有错误前提下

44420

百度不问我项目,全程基础拷打,真扎心!

是否可以被重载:opeartor new /operator delete可以被重载。而malloc/free则不能重载。...这是因为在使用delete操作符释放一个指向派生类对象基类指针时,如果基类析构函数不是虚函数,那么只会调用基类析构函数,而不会调用派生类析构函数,这样就会导致内存泄漏和未定义行为问题。...通过将析构函数定义为虚函数,可以确保在释放派生类对象时,先调用派生类析构函数,再调用基类析构函数,从而避免内存泄漏和未定义行为问题。...右值引用有什么作用 没用过 补充: 右值引用是C++11引入特性,它是指右值进行引用一种方式。右值引用作用主要有两个: 可以通过右值引用来实现移动语义。...如果遇到内存泄漏这种问题,你一般是怎么去解决 打断点定位然后做处理 后来思考对方应该是想让我回答这种处理措施⬇️ 在程序中加入必要错误处理代码,避免程序因为异常情况而导致内存泄漏。

21810
领券