C++函数

 

转载知呼大佬06 - C++函数 - 知乎 (zhihu.com)

06 - C++函数

 

本期我们讨论的是 C++ 中的函数。

函数到底是什么呢,函数就是我们写的代码块,被设计用来执行特定的任务,以后我们学习 class 类的时候,这些块会被称为方法,但是当我说到函数时,我们讲的可不是 C++ 类里面的 方法。

01 函数能干什么

对我们来说,使用函数是很常见的,避免代码重复。我们不想重复写相同的代码,当然,如果我们也可以复制和粘贴很多代码,但会导致巨大的混乱,这也意味着如果我们决定改变一些代码,我们必须在所有这些地方改变它,我们粘贴的地方,那维护这些代码简直就是灾难,所以我们把我们要做的事情写成一个函数,然后可以多次调用它。

如果需要的话,你可以认为函数有一个输入,一个输出,尽管他们可能并不需要这么做。我们可以为函数提供一定的参数,函数可以为我们返回值。

02 定义函数

假设我们想把两个数相乘,我们想写出这样的一个函数。

 

format,png

我们对上面的代码做一些详细的解释。

首先写的是所谓的返回值 int,也就是说,这就是这个函数的返回类型,因为是两个整数相乘,这当然会得到一个整数 ;然后给出函数名 multiply ,它有两个参数 a 和 b ,这些就是我们要乘的数,它们的类型都是 int。然后给出函数体,它会返回 a*b 。

这样你就得到一个函数,它有两个都是整数的参数,该函数的功能是返回两者的乘积。

我们不一定非要提供参数,例如,我可以不提供任何参数,直接返回 5*8 ,这仍然是一个返回整数的函数,但它没任何参数。

 

format,png

我们也可以让函数不返回任何东西,我们通过写 void 作为返回类型来实现,void 意思是啥也没有,所以我们可以这样做。

 

format,png

03 调用函数

如何调用这个函数呢?调用一个函数非常简单,我们直接看下面的例子。

 

format,png

对上面的代码我们做一些解释。

首先我们定义了一个变量 result,来装这个结果,然后直接写函数的名字加括号就可以完成调用函数,括号里面的数字就是函数需要的两个参数,返回值 result 保存 a*b 的结果,最后我们将结果输出到控制台。按 F5 来运行程序,你可以看到我们得到显示是6,也就是2乘以3的结果。

04 为什么要用函数

所以,为什么要用函数呢?看起来代码还更多了一些。

让我们把情况说的更详细些,假设我要做一堆的乘法,我想把它们都记录到控制台,在没有函数的情况下,下面的情况这样看起来会很乱。

 

format,png

如果你运行了这些代码,你会发现我犯了一些错误,我想说的是,其实这种情况经常发生。人们复制和粘贴代码块, 然后忘记改变一个小细节,在某些情况下程序如果正常运行的话,你就有可能注意不到,直到它在某个地方出错了,你才会知道。

(你不会还没发现错在哪里吧?)

让我们修正这些代码。

 

format,png

这样我们会得到正确的结果。

上面的多段代码大部分内容基本差不多,基本的区别就是参与乘法的数字不同。这就很难受了。

让我们为这个重复的过程创建一个函数。

先分析一下具体的需求。这个函数应该不需要返回值,它只需要输出一些信息;这个函数需要两个参数,就可以完成每段代码中不同的部分;为了直观的联想到函数的功能,函数的名字就叫做 MultiplyAndLog 吧,然后我们就有了下面这个函数。

 

format,png

函数定义好后,我们要做的就是调用这个函数。

 

format,png

如果启动这个程序, 你可以看到,在这里可以获得正确的值,这是一个很简单的例子,我们获得了一个非常干净、易于阅读的程序。

通过以上给分析过程,我们有效地证明了函数是真的非常重要的。你的目标应该是将你的代码分开成很多函数。

然而, 有一件事我想强调,也不要把你的代码每一行都拆成函数,对任何人都没有好处的代码,这很难维护,您的代码将看起来凌乱不堪,它会让你的程序变慢。

原因是每次我们调用函数时,编译器生成一个call 指令,这基本上意味着,在一个运行的程序中,我们需要创建一个堆栈结构,这意味着我们必须把像参数这样的东西推进堆栈,我们还需要将一个叫做返回地址的东西,然后我们要做的是跳到二进制执行文件的不同部分,以便开始执行我们的函数指令。为了将 push 进去的结果返回,我们得回去到最初调用函数之前。就像在内存中跳跃来执行函数,跳跃和执行这些都需要时间,这些会减慢我们的程序。当然前提是保持我们当前的函数是作为一个实际的函数,而不是做内联inline的工作(我们会在未来深入讨论内联)。

我说这些都是因为不想让你们对于每一行代码都去创建函数,不要做那么搞笑的事情,编码多了你才能明白哪里你会需要一个函数,但基本上如果你看到自己在多次做一项共同的任务,那么基本可以为此创建一个函数,函数的主要目的是防止代码重复,我们不希望复制粘贴代码。

05 其他的

现在我们回到代码中,有些小伙伴会发现一个细节,main 函数需要返回 int 类型的值,可是在 main 函数体中却找不到 return 关键字。这样操作是合理的吗?

然我们做一个修改,验证一些东西。

 

format,png

Ctrl+F7 编译,我们得到了一个错误。

 

format,png

看起来有返回类型的函数的确必须有返回值。

原因是主函数实际上是一个特殊函数,只有主函数被豁免可以不返回值,它会自动假设你返回0。其他的函数必须要返回值。 main函数不写返回值的操作只是现代 C 和C++ 的一个特性,可以让你代码保持的干净一点。

好了,我们知道这必须返回一个值,刚才讲的东西实际上 只适用于调试模式,如果我们在release 模式下编译,这里你会看到我们没有得到错误,这并不是说我们现在做的是正确的,因为如果我们真的要拿返回值值做某些事情的话,我们会得到 “未定义的行为” 的报错信息,只是编译器不会报错,但是在调试模式下,编译器就会显示出错。

后话

好了,这是一个基本的函数介绍,函数真的很有用。未来我还会写很多函数,每个程序都是由一系列函数组成的,所以这是非常重要的,如果你不认为你完全理解函数是如何工作的,不用担心, 因为在这个系列中我们会写超级多的函数,你会掌握它的,最好的学习方法当然是多练习是吧。我们通常还将函数分解为声明和定义,声明通常存储在头文件中,我们在转换单元或 CPP 文件中编写定义,我将专门制作关于头文件的一期,在那里会讲到在头文件中函数如何声明。

 

 

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

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

相关文章

windows排除扫描文件夹

搜索防火墙和网络保护 点击病毒和威胁防护 往下拉,找到排除项 添加排除项

MySQL InnoDB 引擎底层解析(三)

6.3.3. InnoDB 的内存结构总结 InnoDB 的内存结构和磁盘存储结构图总结如下: 其中的 Insert/Change Buffer 主要是用于对二级索引的写入优化,Undo 空间则是 undo 日志一般放在系统表空间,但是通过参数配置后,也可以用独立表空 间…

【C++上层应用】2. 预处理器

文章目录 【 1. #define 预处理 】【 2. #ifdef、#if 条件编译 】2.1 #ifdef2.2 #if2.3 实例 【 3. # 和 ## 预处理 】3.1 # 替换预处理3.2 ## 连接预处理 【 4. 预定义宏 】 预处理器是一些指令,指示编译器在实际编译之前所需完成的预处理。 所有的预处理器指令都是…

分类预测 | Matlab实现基于PSO-SDAE粒子群优化算法优化堆叠去噪自编码器的数据分类预测

分类预测 | Matlab实现基于PSO-SDAE粒子群优化算法优化堆叠去噪自编码器的数据分类预测 目录 分类预测 | Matlab实现基于PSO-SDAE粒子群优化算法优化堆叠去噪自编码器的数据分类预测分类效果基本描述程序设计参考资料 分类效果 基本描述 1.Matlab实现基于PSO-SDAE粒子群优化算法…

Flutter笔记:使用相机

Flutter笔记 使用相机 作者:李俊才 (jcLee95):https://blog.csdn.net/qq_28550263 邮箱 :291148484163.com 本文地址:https://blog.csdn.net/qq_28550263/article/details/134493373 【简介】本文介绍在 Fl…

听GPT 讲Rust源代码--src/librustdoc

题图来自 Why is building a UI in Rust so hard? File: rust/src/librustdoc/core.rs 在Rust中,rust/src/librustdoc/core.rs文件的作用是实现了Rustdoc库的核心功能和数据结构。Rustdoc是一个用于生成Rust文档的工具,它分析Rust源代码,并生…

git基本操作(配图超详细讲解)

个人主页:Lei宝啊 愿所有美好如期而遇 目录 创建git本地仓库 配置仓库 认识工作区,暂存区,版本库 修改文件 版本回退 撤销修改 删除文件 创建git本地仓库 要提前说的是,仓库是进⾏版本控制的⼀个⽂件⽬录。我们要想对⽂…

linux网络——HTTPS加密原理

目录 一.HTTPS概述 二.概念准备 三.为什么要加密 四.常⻅的加密⽅式 1.对称加密 2.⾮对称加密 五.数据摘要,数字签名 六.HTTPS的加密过程探究 1.方案一——只使用对称加密 2.方案二——只使⽤⾮对称加密 3.方案三——双⽅都使⽤⾮对称加密 4.方案四——⾮…

stack和queue简单实现(容器适配器)

容器适配器 stack介绍stack模拟实现queue 介绍queue模拟实现deque stack介绍 stack模拟实现 以前我们实现stack,需要像list,vector一样手动创建成员函数,成员变量。但是stack作为容器适配器,我们有更简单的方法来实现它。 可以利用模板的强大…

go语言学习之旅之Go 语言指针

学无止境,今天继续学习go语言的基础内容 Go语言支持指针,允许你在程序中直接操作变量的内存地址。指针存储了变量的内存地址,通过指针,你可以直接访问或修改该地址上的值。 学习过c语言的一定知道指针 定义指针 在Go语言中&…

AC修炼计划(AtCoder Beginner Contest 329)

传送门:Sky Inc, Programming Contest 2023(AtCoder Beginner Contest 329) - AtCoder A,B,C,D 这四道题比较简单,就不多叙述。 E - Stamp 这题是一道比较…

VMware——WindowServer2012R2环境安装mysql5.7.14解压版_主从复制(图解版)

目录 一、服务器信息二、192.168.132.33主服务器上安装mysql(主)2.1、环境变量配置2.2、安装2.2.1、修改配置文件内容2.2.2、初始化mysql并指定超级用户密码2.2.3、安装mysql服务2.2.4、启动mysql服务2.2.5、登录用户管理及密码修改2.2.6、开启远程访问 …

Linux C 网络编程概述

网络编程 计算机网络概述分类网络体系结构通信协议通信流程网络通信帧格式以太网帧格式分析ARP 协议分析IP 数据报分析IP分类IP 分配子网掩码 TCP 段分析 TCP三次握手协议 ⭐TCP四次挥手协议 ⭐ TCP编程基于 TCP 客户端编程-步骤说明基于 TCP 服务器端编程-步骤说明基于 TCP 服…

苍穹外卖项目笔记(2)

1 Nginx 反向代理和负载均衡 1.1 概念 【Tips】可以看到前端请求地址和后端接口地址并不匹配,这里涉及到 nginx 反向代理 ,就是将前端发送的动态请求由 nginx 转发到后端服务器 使用 nginx 作反向代理的好处: 提高访问速度(在请…

Vue3 customRef自定义ref 实现防抖

防抖就是防止在input 框中每输入一个字符就要向服务器请求一次,只要在用户输入完成过一段时间再读取用户输入的内容就能解决这个问题,减小服务器的压力。 1. 自定义ref是一个函数,可以接受参数。 比如我们自定义一个myRef: setu…

二进制位(计算机存储数据最小单位)

二进制数据中的一个位(bit)简写为b,音译为比特,是计算机存储数据的最小单位。一个二进制位只能表示0或1两种状态,要表示更多的信息,就要把多个位组合成一个整体,一般以8位二进制组成一个基本单位。计算机内部数据以二进…

美团面试:微服务如何拆分?原则是什么?

尼恩说在前面 在40岁老架构师 尼恩的读者交流群(50)中,最近有小伙伴拿到了一线互联网企业如美团、字节、如阿里、滴滴、极兔、有赞、希音、百度、网易的面试资格,遇到很多很重要的面试题: 微服务如何拆分? 微服务拆分的规范和原则…

Shell判断:模式匹配:case(二)

简单的JumpServer 1、需求:工作中,我们需要管理N多个服务器。那么访问服务器就是一件繁琐的事情。通过shell编程,编写跳板程序。当我们需要访问服务器时,看一眼服务器列表名,按一下数字,就登录成功了。 2、…

在Vue3中使用Element-Plus分页(Pagination )组件

开发过程中数据展示会经常使用到&#xff0c;同时分页功能也会添加到页面中。 记&#xff1a;在Vue3中使用Element-Plus分页组件与表格数据实现分页交互。 开始实现 引入表格和分页组件的H5标签。 <strong>Element-Plus分页组件使用</strong> <div><el-t…

Windows配置全局代理

一. Windows下为PowerShell/CMD/Git设置代理 —————————————————————————————————————————————————————— 二. [WinError 10061] 由于目标计算机积极拒绝&#xff0c;无法连接。 keyerror:192。 HTTP Error 403: Forbidd…