C++中返回类型与return语句

C++中返回类型与return语句

有、无返回值的函数及其return语句
无返回值(函数声明中,返回值类型为void)的函数,如果其中没有任何return语句也是正确的,编译器会自动在函数结束处补上隐式的return;语句。如果这种void函数内部出现显式的return;,其作用是表示该函数在此处将控制权交还给主调函数。
除void函数外,其他函数必须显式地返回与声明中返回值类型相同(或可以转换为该类型)的值。
函数把值返回给调用处的细节原理
函数把值返回给外部调用处的实现方法细节与从外部实参传递值给函数形参的方法细节完全一样。本质上是用已有值(传参中的实参,返回中的返回值)初始化一个临时量(传参中的形参,返回中的函数调用点)。因此对象的初始化规则在函数返回过程中仍然适用。

1 函数返回局部变量给外部
本质上是将函数内局部变量的值拷贝给函数调用点,用来初始化(外部)调用点的临时对象。

2 函数返回引用给外部
引用是对象的别名,因此此时函数对外返回的是对象本身,而不是拷贝一个值给外部副本。因此要特别注意,千万不能返回函数内部局部对象的引用和指针。因为函数在结束调用后局部变量就会被销毁,这时被函数给返回到外部的局部变量对象(引用)将不再绑定有效的内存区域。

综上可知,函数要想对外返回引用(或指针),只能返回那种在函数调用之前已经存在了的对象的引用(或指向该对象的指针)

范例:

//函数对外返回引用的正确用法
const string &shorterStr(const string &s1, const string &s2) { //挑出两个string对象中较短的那个,返回其引用return s1.size() <= s2.size() ? s1 : s2; //因为s1和s2绑定的对象都是在调用函数前就已经存在的了,因此函数对外返回这种对象的引用不会产生问题
}//以下写法严重错误,这个函数试图返回局部对象的引用
const string &manip() {string ret;if (!ret.empty()) {return ret; //❌,试图返回局部对象的引用} else {return "Empty"; //❌,"Empty"也是一个局部临时量,并且以引用的方式传出,在函数结束调用后该临时量会被销毁,使得外部调用点的引用不再绑定具体对象}
}//以下写法严重错误,不能返回一个指向局部对象的指针
int *funcIp(int var) {int i = 10;int *ip = &(i + var); //i + var对象是一个临时量,结束调用后销毁,对外返回的指针无法指向确定的内存return ip;
}

返回类类型的函数可以连续调用
返回类类型(类的对象或其引用,或指向类的对象的指针)的函数,可以在其调用处继续使用调用运算符去调用该类的其他函数,如下例:

const string &shorterStr(const string &s1, const string &s2) { //此函数返回的是一个string对象的引用return s1.size() <= s2.size() ? s1 : s2; 
}
string s1 = "aaaa";
string s2 = "bbb";
auto sz = shorterStr(s1, s2).size(); //shoterStr(s1, s2)返回的是一个string对象(s2),该对象有size()成员函数,因此可以在shoterStr()的返回处再继续调用size(),这个调用结束后,返回的是一个size_t类型值对象,由auto类型对象sz接收

引用返回左值
调用一个返回引用的函数,在调用处得到左值(左值可以放在赋值号左边用来被赋值)
调用返回其他类型的函数,在调用处得到右值(右值可以放在赋值号右边用来赋值)
可以像使用其他左值那样来使用返回左值(返回引用)的函数调用,特别是能为返回类型是非常量引用的函数结果进行赋值。如下例:
但如果函数的返回值类型是常量引用,就不能给调用结果进行赋值了,这是常量特性所决定的

char &get_val(string &str, string::size_type ix) { //该函数的返回值类型是非常量引用,其返回结果可以在调用处被当作左值return str[ix]; //假定索引值ix一定合法
}const string &shorterStr(const string &s1, const string &s2) { //此函数返回的是常量引用return s1.size() <= s2.size() ? s1 : s2; 
}int main() {string s("a value");cout << s << endl; //输出:a valueget_val(s, 0) = 'A'; //get_val的返回结果在此处被当作左值,因为它的返回值类型是非常量引用,可以完成这里的赋值操作,将s[0]的值改为Acout << s << endl; //输出:A valueshoterStr("hi", "bye") = "X"; //❌,返回的是常量引用(也就是常量对象),不能被修改,因此也不能这样作为左值使用return 0;
}

该文章会更新,欢迎大家批评指正。

推荐一个零声学院的C++服务器开发课程,个人觉得老师讲得不错,
分享给大家:Linux,Nginx,ZeroMQ,MySQL,Redis,
fastdfs,MongoDB,ZK,流媒体,CDN,P2P,K8S,Docker,
TCP/IP,协程,DPDK等技术内容
点击立即学习:C/C++后台高级服务器课程

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/83083.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

VOP —— Noise

目录 Turbulent Noise —— 计算1D/3D类型的Noise Anti-Aliased Flow Noise —— 生成抗锯齿噪波 Anti-Aliased Noise —— 生成抗锯齿噪波 Curl Noise —— 创建divergence-free 3D噪波 Curl Noise 2D —— 创建divergence-free 2D噪波 Flow Noise —— 生成1D/3D Perli…

理解Kruskal算法的前提----深入理解并查集【超简单~】

并查集的实现思路 并查集主要分为两个部分&#xff1a;第一部分就是需要找到点对应的祖宗节点&#xff0c;第二部分&#xff0c;是要将属于同一个集合节点的祖宗节点进行统一&#xff0c;也就是结合操作。 Find函数实现 // parent数组用来存储下标值所对应的父节点值 // 比如…

下载安装nvm教程(附带下载切换node.js版本实操)

目录 一、介绍 二、下载 三、安装步骤 四、配置淘宝源 五、测试 六、常用的nvm命令 七、下载切换node版本实操 node版本参考 一、介绍 node版本管理&#xff1a;nvm就是可以切换你的node版本&#xff0c;特别是当node版本过高或者过低时候&#xff0c;就可以用nvm进行…

036:vue导出页面生成pdf文件

第036个 查看专栏目录: VUE ------ element UI 专栏目标 在vue和element UI联合技术栈的操控下&#xff0c;本专栏提供行之有效的源代码示例和信息点介绍&#xff0c;做到灵活运用。 &#xff08;1&#xff09;提供vue2的一些基本操作&#xff1a;安装、引用&#xff0c;模板使…

GIF动图怎么变成jpg动图?一键分解GIF动画

GIF格式图片怎么转换成jpg格式图片&#xff1f;在日常生活中jpg、png转GIF格式非常的常见&#xff0c;那么gif转换成jpg格式应该怎么操作呢&#xff1f;很简单&#xff0c;给大家分享一款gif动态图片制作&#xff08;https://www.gif.cn/giffenjie&#xff09;工具&#xff0c;…

Oracle Schema Only账户

概念 Schema Only Accounts是Oracle 18c的新安全功能&#xff0c;19c进一步增强。 19c的增强其实就是允许此账户有管理权限&#xff1a;Ability to Grant or Revoke Administrative Privileges to and from Schema-Only Accounts A schema only account cannot log in to the…

计算机视觉与深度学习-卷积神经网络-纹理表示卷积神经网络-卷积神经网络-[北邮鲁鹏]

这里写目录标题 参考文章全连接神经网络全连接神经网络的瓶颈全连接神经网络应用场景 卷积神经网络卷积层(CONV)卷积核卷积操作卷积层设计卷积步长(stride)边界填充特征响应图组尺寸计算 激活层池化层(POOL)池化操作定义池化操作作用池化层超参数常见池化操作 全连接层(FC)样本…

设计心理学-日常操作心理学 优漫动游

大师解释了产品设计的几个原则后&#xff0c;接着其实就是解释日常生活中用户操作的心理&#xff0c;从深层次的角度&#xff0c;解释为什么产品设计需要依据这些原则。 设计心理学-日常操作心理学 首先书中提出了一个显而易见的概念&#xff1a;用户习惯自行判断产品的功…

算法通关村 | 透彻理解动态规划

1. 斐波那契数列 1&#xff0c;1&#xff0c;2&#xff0c;3&#xff0c;5&#xff0c;8&#xff0c;13&#xff0c;..... f(n) f(n-1) f(n-2) 代码实现 public static int count_2 0;public int fibonacci(int n){if (n < 2){count_2;return n;}int f1 1;int f2 2;i…

C++入门及简单例子_4

1. 类和对象&#xff1a; #include <iostream> // 包含输入输出流库的头文件class Rectangle { // 定义名为Rectangle的类 private: // 私有成员变量部分double length; // 长度double width; // 宽度public: // 公有成员函数部分Rectangle(double len, double w…

【鸽鸽送书第一期】 | 实现可观测性平台的技术要点是什么?文末参与送书哦!

&#x1f3ac; 鸽芷咕&#xff1a;个人主页 &#x1f525; 个人专栏:《粉丝福利》 《C语言进阶篇》 ⛺️生活的理想&#xff0c;就是为了理想的生活! 文章目录 &#x1f4cb; 前言实现可观测性平台的技术要点是什么&#xff1f;1.兼容全域信号量2.所谓全域信号量有哪些&#x…

Java 对象和类

目录 Java 对象和类 Java中的对象 Java中的类 构造方法 创建对象 访问实例变量和方法 源文件声明规则 Java包 Import语句 一个简单的例子 Java 对象和类 Java作为一种面向对象语言。支持以下基本概念&#xff1a; 多态继承封装抽象类对象实例方法消息解析 本节我们重…

基于AI视觉的表面缺陷检测设备优势显著,加速制造业数智化转型

作为生产制造过程中不可缺少的一步&#xff0c;表面缺陷检测广泛应用于工业领域&#xff0c;包括3C电子、芯片半导体、食品医药、木材等行业。但随着智能化进程加快&#xff0c;制造工厂生产线的质量检测压力加剧&#xff0c;传统人工表面缺陷检测已经无法满足当前社会较高的检…

YOLOv8『小目标』检测指南

前言 目前博主课题组在进行物体部件的异常检测项目&#xff0c;项目中需要先使用 YOLOv8 进行目标检测&#xff0c;然后进行图像切割&#xff0c;最后采用 WinCLIP 模型 进行部件异常检测 但是在实际操作过程中出现问题&#xff0c; YOLOv8 模型目标检测在大目标精确度不错&a…

Mybatis深度解析:从起源到现代应用的全景视角

&#x1f337;&#x1f341; 博主猫头虎 带您 Go to New World.✨&#x1f341; &#x1f984; 博客首页——猫头虎的博客&#x1f390; &#x1f433;《面试题大全专栏》 文章图文并茂&#x1f995;生动形象&#x1f996;简单易学&#xff01;欢迎大家来踩踩~&#x1f33a; &a…

Centos7部署单机版MongoDB

目录 Centos7部署单机版MongoDBMongoDB介绍数据模型索引分布式高可用性查询语言驱动和社区用途缺点 下载并解压安装包创建相关文件夹和文件编辑mongod.conf文件启动mongodb创建管理员用户终止MongoDB服务配置自启动服务关闭SELinux编辑自启动服务文件mongodb服务命令 Centos7部…

spark6. 如何设置spark 日志

spark yarn日志全解 一.前言二.开启日志聚合是什么样的2.1 开启日志聚合MapReduce history server2.2 如何开启Spark history server 三.不开启日志聚合是什么样的四.正确使用log4j.properties 一.前言 本文只讲解再yarn 模式下的日志配置。 二.开启日志聚合是什么样的 在ya…

Debian

常用命令 apt-get apt list --installed查找特定的软件包&#xff0c;使用grep命令过滤结果 apt list --installed | grep package_name卸载&#xff0c;apt purge [安装包] apt purge package_name报错 缺少公钥 错误信息&#xff1a; GPG error: http://security.ubun…

QT-day1

实现华清远见登陆界面 #include "mywnd.h" #include <iostream> #include <QDebug> #include <QPushButton> #include <QLineEdit> #include <QLabel>MyWnd::MyWnd(QWidget *parent): QWidget(parent) {//设置固定窗口大小长400&…

【计算机毕业设计】基于SpringBoot+Vue的小区物业管理系统的设计与实现

博主主页&#xff1a;一季春秋博主简介&#xff1a;专注Java技术领域和毕业设计项目实战、Java、微信小程序、安卓等技术开发&#xff0c;远程调试部署、代码讲解、文档指导、ppt制作等技术指导。主要内容&#xff1a;毕业设计(Java项目、小程序等)、简历模板、学习资料、面试题…