C++ 重载运算符返回值 和 返回引用的原因
原因是:
+,-,*等返回不了引用,比如+运算符,可以如下重载(为了简单,假设A 只有int x;int y)
A operator+(A a,A b) {A sum; sum.x=a.x+b.x; sum.y=a.y+b.y; return sum; }
分析不能用引用的原因: 函数传入了两个参数a,b,并且+只能传入两个参数(c++不允许自己创造运算符),这样就限定了和sum不能作为参数传入,所以sum只能是一个函数里的临时变量,但是临时变量在函数结束时是要销毁的,那么函数调用玩,sum就没有了, 如果返回引用,引用源都已经没有了,还怎么引用,引用哪里的东西呢??
所以不能引用。
<<,>>可以返回引用,而且不返回引用也是编译不过的,貌似是c++的要求。可以不用引用试一试,有的编译器会出来一个ios_base.h文件,就是想告诉你用引用。
返回引用也是可以解释的。 比如还是上面的A类型,如下
ostream& operator<<(ostream& out, const A& a) { out<<A.x<<' '<<A.y<<endl; retrun out;}
能返回引用,首先是因为out是作为参数传入的,不是函数的临时变量,函数结束时它仍然存在,这样就可以引用了。 再者,返回引用效率高,不用拷贝一个新的,直接返回它自己。 而且,返回引用有助于连着调用。比如cout<<a<<b<<c<<d,为什么可以连着写?其实<<也是函数,为什么我们平时的函数一般不能连着写?如a.xx().xx().xx.()这样调用三个xx()。这也体现了引用的作用。 对于cout<<a<<b<<c<<d;就是
operator<<(operator<<(operator<<(operato<<(cout,a),b),c),d);
从左到右先执行cout<<a执行完了后返回cout的引用,就是cout本身,那么原式变为cout<<b<<c<<d; 紧接着这行cout<<b执行完再次返回cout........这样就把a,b,c,d依次作用到了cout,我们于是看到abcd连续输出了。
如你所说,cout<<a<<b<<c<<d;谭浩强说,先执行cout<<a,返回一个输出流对象(引用),然后这个新的cout对象(引用)又执行<<b,然后又返回一个新的cout对象(引用),直到输出完成。每输出一次,就返回一个新的输出流对象(引用),那每次输出流对象cout有啥不同。
一般可以认为第一次执行完cout直接将a输出到了屏幕,cout本身没有变化,然后执行b......
但是具体情况不是这样的。这要看c++的IO具体是怎么设计的。执行一次cout<<a并不一定直接将a输出到屏幕,而是将a转到IO的缓冲区,具体什么时候将a输出到屏幕要看系统什么时候有时间和c++的IO具体是怎么实现的。 系统掌握着消息队列,每次从里面抽取一条消息执行,因为CPU效率很高,我们感觉程序是连续运行的,其实不连续。对于多核处理器来说可以发生真实的同时执行几个程序。
要强制系统将数据输出到屏幕上,可以“刷新”一下,比如用cout<<endl;就是打一个换行,再刷新缓冲区,刷到屏幕上。
对于评论区的两点,解释一下:
重载<<流输出运算符,我是用于一个自定义类与ostream类,不是重载<<的移位运算等,不用做其他用法。 在我的编译器上不通过(VS2012和DEV c++都编译不通过)
我举得例子有错误,为了简便直接写的,现在发现是错的。因为都是A的对象相加,如果有两个参数,那么应该是友元函数,frined ......, 如果一个参数,可以声明为成员函数。
至于为什么返回引用也正常,这是由于:
“函数返回的临时变量是放在堆栈上的,所以返回来后如果你没有调用其他的函数,那么这个临时变量在依然保存在堆栈中,是可以被引用的。
因为这时堆栈并没有被破坏。但是一旦调用其他函数后堆栈被破坏了,那个返回值就没有用了”摘自“正心修身齐家治国平天下”的百度空间,可以看一下。
即使这样编译器也会给警告(WARNING),不建议这么写
===================以上摘自百度https://zhidao.baidu.com/question/917635728677386659.html
C++ 重载运算符返回值 和 返回引用的原因的更多相关文章
- shell函数(调用、返回值,返回值获取)
Shell函数返回值,常用的两种方式:return,echo 1) return 语句shell函数的返回值,可以和其他语言的返回值一样,通过return语句返回.示例1: [devadmin@swa ...
- scala:函数作为值或参数进行传递、作为返回值进行返回
@ 目录 函数可以作为值进行传递 函数可以作为参数进行传递 函数可以作为返回值进行返回 什么是匿名函数 函数可以作为值进行传递 语法var f = 函数名 _ 如果明确了变量的数据类型,那么下划线可以 ...
- 【C/C++】引用&的含义/语法/作为函数参数/函数返回值/本质/常量引用
含义 引用不产生副本,只是给原变量起了别名. 对引用变量的操作就是对原变量的操作. 基本语法 数据类型 &别名 = 原名 e.g. int a = 10; int &b = a; // ...
- Java学习笔记14---this作为返回值时返回的是什么
有时会遇到this作为返回值的情况,那么此时返回的到底是什么呢? 返回的是调用this所处方法的那个对象的引用,读起来有点绕口哈,有没有想起小学语文分析句子成份的试题,哈哈. 一点点分析的话,主干是& ...
- std::vector<bool> 在 auto 推断下的返回值是 bool & 引用
转自: https://www.cnblogs.com/hustxujinkang/p/5218148.html //////////// std::vector<bool> featur ...
- python操作mysql数据-执行语句返回值直接返回字典类型
fetchall()将结果放在二维数组里面,每一行的结果在元组里面 import pymysql def export(table_name): conn =pymysql.connect(host ...
- $.extend(obj1,obj2...,objN)小结 扩展obj1属性,有返回值,返回第一个被扩展后的对象
<script> var obj1 = { name:'liu', age:'24' } var obj2 = { name:'jinyu', sex:'m ...
- Python3基础 函数 未指定返回值,返回NONE
Python : 3.7.0 OS : Ubuntu 18.04.1 LTS IDE : PyCharm 2018.2.4 Conda ...
- C#7.0--引用返回值和引用局部变量
一.在C#7.0以上版本中,方法的返回值可以通过关键字ref指定为返回变量的引用(而不是值)给调用方,这称为引用返回值(Reference Return Value,或ref returns): 1. ...
随机推荐
- leaflet使用手册
谷歌地图加载地址: 谷歌交通地图地址:http://www.google.cn/maps/vt/pb=!1m4!1m3!1i{z}!2i{x}!3i{y}!2m3!1e0!2sm!3i38007257 ...
- 【caffe Net】使用举例和代码中文注释
首先是Net使用的小例子: #include <vector> #include <iostream> #include <caffe/net.hpp> using ...
- VsCode插件与Node.js交互通信
首先关于VsCode插件通信,如果不明白的可以参考我的这篇博客VsCode插件开发之插件初步通信 如果需要详细例子的话,可以参考VsCode插件开发 现在又有一个新的需求是,VsCode插件可以通过j ...
- [Android] 安卓手机不用root删除自带app
声明:本文档仅供测试,因删除引起的一切问题,本人概不负责 声明:本文档仅供测试,因删除引起的一切问题,本人概不负责 声明:本文档仅供测试,因删除引起的一切问题,本人概不负责 转载请注明出处:https ...
- SQL语句简单增删改查
常用数据类型 Int:整数,长度没有作用 Varchar:字符串,varchar(3)表示最多存放3个字符,1个中文或英文或符合都占1个字符 Decimal:小数,decimal(5,2)表示共存5位 ...
- 深度学习面试题28:标签平滑(Label smoothing)
目录 产生背景 工作原理 参考资料 产生背景 假设选用softmax交叉熵训练一个三分类模型,某样本经过网络最后一层的输出为向量x=(1.0, 5.0, 4.0),对x进行softmax转换输出为: ...
- CopyOnWrite 思想及在 Java 并发包中的具体体现
读多写少的场景下引发的问题? 假设现在我们的内存里有一个 ArrayList,这个 ArrayList 默认情况下肯定是线程不安全的,要是多个线程并发读和写这个 ArrayList 可能会有问题. 那 ...
- markdown2的key
分享一个MarkDown2的授权key 邮箱地址: Soar360@live.com 授权秘钥: GBPduHjWfJU1mZqcPM3BikjYKF6xKhlKIys3i1MU2eJHqWGIm ...
- 【转】暴力破解无线WiFi密码
# coding:utf-8 import pywifi from pywifi import const import time from asyncio.tasks import sleep cl ...
- PLSQL流函数代码 540页 【我】
540页 流函数代码 -- Create table create table STOCKTABLE ( TICKER ), TRADE_DATE DATE, OPEN_PRICE NUMBER, C ...