C语言中的函数,实参,形参,递归
1:什么是函数
2:定义带形式参数的函数和带实际参数的函数
3:递归
---------------------------------------------------------------------------------------------------------------------------------
1:在 C 语言中,函数是一个可重复使用的代码块,用于执行特定任务或计算。它可以接收输入(称为参数),执行代码,并根据需要返回一个值。函数有助于将程序分解为更小、易于管理的部分,促进代码的复用和组织。
函数的特点:
-
封装性:函数将特定的功能或逻辑封装在一个独立的代码块中,外界只需调用函数,而无需关心内部实现。
-
参数传递:可以通过参数将数据传递给函数,函数根据传入的参数执行不同的操作。
-
返回值:函数可以通过
return语句将结果返回给调用者。 -
代码复用:定义一次函数,可以在多个地方调用,避免重复代码。
函数的组成:
- 函数声明(或函数原型):提供给编译器关于函数的返回类型、名称及参数类型的信息。
- 函数定义:指定函数的实际实现,包括要执行的代码。
- 函数调用:执行函数时通过名称调用函数,并传递必要的参数。
----------------------------
2:在 C 语言中,定义带形式参数(也称为形参)的函数时,函数的定义包含参数的类型和名称。这些形参在函数定义中使用,用于接收调用函数时传递的实际参数(也称为实参)。形参相当于函数的占位符,实参会在函数调用时赋值给形参。
定义带形式参数的函数的基本格式:
返回类型 函数名(参数类型1 形参名1, 参数类型2 形参名2, ...) {// 函数体return 返回值; // 如果有返回值
}
关键点:
- 形参:在函数定义的参数列表中,指定参数类型和名称。形参仅在函数内部有效,函数外部无法访问。
- 参数传递:函数调用时,将实参传递给形参,形参接受对应的数据并用于函数内部操作。
示例:带形式参数的函数
#include <stdio.h>// 函数定义:接收两个整数作为参数,并返回它们的和
int add(int a, int b) {return a + b; // 使用形参 a 和 b
}int main() {int x = 5;int y = 3;// 函数调用,将实参 x 和 y 传递给形参 a 和 bint result = add(x, y);printf("%d + %d = %d\n", x, y, result); // 输出结果return 0;
}
解释:
- 形参:
a和b是add函数的形式参数,它们在函数内部用于计算。 - 实参:在
main函数中,x和y是实际参数,调用add(x, y)时,x的值传递给a,y的值传递给b。
示例:带多个形式参数的函数
#include <stdio.h>// 函数定义:计算矩形的面积
int calculateArea(int length, int width) {return length * width;
}int main() {int l = 10;int w = 5;// 函数调用,将实参 l 和 w 传递给形参 length 和 widthint area = calculateArea(l, w);printf("The area of the rectangle is: %d\n", area);return 0;
}
解释:
- 形参:
length和width是函数calculateArea的形参。 - 实参:在
main中,l和w是实参,调用calculateArea(l, w)时,l传递给length,w传递给width,并计算矩形的面积。
------------------------------------
递归(Recursion)是指在程序或函数中调用自身的一种编程技术。递归是一种解决问题的方法,通过将问题分解为规模更小的子问题,直到遇到最小的子问题(称为基准情况),然后再逐步解决这些子问题。
在 C 语言中,递归函数是指直接或间接调用自己的函数。递归函数必须有一个基准条件(base case)来防止无限递归,否则程序将导致栈溢出(Stack Overflow)。
递归的基本结构:
递归函数一般包含两部分:
- 基准条件(Base case):递归终止条件,防止函数无限调用自身。
- 递归条件(Recursive case):函数在适当的情况下调用自身。
递归的基本形式:
返回类型 函数名(参数类型 参数名, ...) {if (基准条件) {// 结束递归,返回结果} else {// 递归调用函数自身}
}
递归示例:计算阶乘
阶乘是递归的经典例子。一个整数 n 的阶乘 n! 定义为:
- 当
n = 0或n = 1时,n! = 1(基准条件)。 - 当
n > 1时,n! = n * (n - 1)!(递归条件)。
#include <stdio.h>// 递归函数:计算 n 的阶乘
int factorial(int n) {if (n == 0 || n == 1) { // 基准条件return 1;} else {return n * factorial(n - 1); // 递归调用}
}int main() {int number = 5;printf("%d! = %d\n", number, factorial(number)); // 输出 5! = 120return 0;
}
解释:
- 基准条件:当
n等于0或1时,返回1,表示递归终止。 - 递归条件:当
n > 1时,函数调用自身,计算n * (n - 1)!。
例如,计算 factorial(5) 时:
factorial(5)会调用factorial(4),factorial(4)调用factorial(3),- 依次类推,直到
factorial(1)返回1,然后逐步返回计算结果,最终得出5! = 120。
递归示例:斐波那契数列
斐波那契数列也是递归的一个常见例子。斐波那契数列的定义是:
F(0) = 0,F(1) = 1(基准条件)。- 对于
n >= 2,F(n) = F(n-1) + F(n-2)(递归条件)。
斐波那契数列的递归实现:
#include <stdio.h>// 递归函数:计算斐波那契数列的第 n 项
int fibonacci(int n) {if (n == 0) { // 基准条件return 0;} else if (n == 1) { // 基准条件return 1;} else {return fibonacci(n - 1) + fibonacci(n - 2); // 递归调用}
}int main() {int number = 10;printf("Fibonacci(%d) = %d\n", number, fibonacci(number)); // 输出第 10 项的斐波那契数return 0;
}
解释:
- 基准条件:
F(0) = 0,F(1) = 1,表示递归的终止条件。 - 递归条件:对于
n >= 2,返回F(n-1) + F(n-2),即前两项之和。
例如,fibonacci(5) 的计算过程如下:
fibonacci(5)=fibonacci(4)+fibonacci(3)fibonacci(4)=fibonacci(3)+fibonacci(2)- 依次类推,直到递归调用到基准条件
fibonacci(0)和fibonacci(1)返回 0 和 1 为止。
递归的优缺点:
优点:
- 简洁易懂:对于一些问题,递归可以将问题的复杂逻辑简化为更直观、易于理解的代码。
- 自然分解:递归非常适合解决那些可以被分解为相同类型子问题的问题,例如树结构、图遍历等。
缺点:
- 性能问题:递归调用会占用更多的栈空间,对于较深的递归调用,可能会导致栈溢出。此外,每次递归调用都涉及函数的创建和销毁,这样会增加开销。
- 效率低:有些递归问题(如斐波那契数列)存在大量重复计算,递归的效率不高,可能需要优化(如使用记忆化技术或改写为迭代形式)。
递归与迭代的比较:
递归和迭代是两种解决问题的不同方法:
- 递归:通过函数调用自身解决问题,依赖于函数的栈结构,通常代码简洁,但效率可能较低。
- 迭代:通过循环结构解决问题,占用的栈空间较少,效率通常更高。
斐波那契数列的迭代实现:
#include <stdio.h>// 迭代方法:计算斐波那契数列的第 n 项
int fibonacci_iterative(int n) {if (n == 0) return 0;if (n == 1) return 1;int a = 0, b = 1, result;for (int i = 2; i <= n; i++) {result = a + b;a = b;b = result;}return result;
}int main() {int number = 10;printf("Fibonacci(%d) = %d\n", number, fibonacci_iterative(number)); // 输出第 10 项的斐波那契数return 0;
}
总结:
- 递归 是解决问题的一种重要技术,通过函数调用自身来解决问题。
- 递归函数必须有一个基准条件,防止无限递归。
- 尽管递归在某些场景下代码简洁优美,但在性能和效率上可能不如迭代,特别是在处理大规模问题时需要谨慎使用。
相关文章:
C语言中的函数,实参,形参,递归
1:什么是函数 2:定义带形式参数的函数和带实际参数的函数 3:递归 --------------------------------------------------------------------------------------------------------------------------------- 1:在 C 语言中&…...
ICM20948 DMP代码详解(15)
接前一篇文章:ICM20948 DMP代码详解(14) 上一回开始对icm20948_sensor_setup函数中第3段代码即inv_icm20948_initialize函数进行解析。为了便于理解和回顾,再次贴出其源码,在EMD-Core\sources\Invn\Devices\Drivers\IC…...
NC 和为K的连续子数组
系列文章目录 文章目录 系列文章目录前言 前言 前些天发现了一个巨牛的人工智能学习网站,通俗易懂,风趣幽默,忍不住分享一下给大家。点击跳转到网站,这篇文章男女通用,看懂了就去分享给你的码吧。 描述 给定一个无序…...
JS设计模式之装饰者模式:优雅的给对象增添“魔法”
引言 在前端开发中,我们经常会遇到需要在不修改已有代码的基础上给对象添加新的行为或功能的情况。而传统的继承方式并不适合这种需求,因为继承会导致类的数量急剧增加,且每一个子类都会固定地实现一种特定的功能扩展。 装饰者模式则提供了…...
准备好了吗?JAVA从业AI开发的学习路线详解
作为一个拥有扎实 Java 基础的人,想要涉足人工智能(AI)应用开发,你已经在编程能力方面打下了很好的基础。Java 是一种通用的、强类型的语言,非常适合于开发高性能的应用程序,尤其是在后端服务和大规模分布式…...
神经网络通俗理解学习笔记(1)
神经网络通俗理解学习笔记(1) 神经网络原理激活函数前向传播和反向传播多层感知机代码实现加载数据网络结构损失函数优化器训练测试保存 回归问题一元线性回归多元线性回归多项式回归 线性回归代码实现数据生成设置超参数初始化参数可视化Pytorch模型实现…...
有n个人,他们需要分配m元钱(m>n),每个人至少分到1元钱,且每个人分到的钱数必须是整数。请问有多少种分配方案?
分配方案 描述 有n个人,他们需要分配m元钱(m>n),每个人至少分到1元钱,且每个人分到的钱数必须是整数。请问有多少种分配方案? 输入 一行,两个整数,分别是人数n与钱数m,用一个空格隔开。 输出 一行&am…...
光耦——创新引擎 助推中国经济高质量发展
近年来,中国经济正处于转型升级的关键时期,高质量发展成为经济发展的重要目标。在这一伟大征程中,光耦作为一种关键性的电子元器件,正在发挥着重要的作用,助力中国经济迈向更加光明的未来。 光耦概念及工作原理 ▲光耦…...
Go 中 RPC 的使用教程
前言 RPC(Remote Procedure Call)是一种允许程序调用远程服务器上函数的方法,调用过程对于开发者来说像是调用本地函数一样方便。Go 语言自带了强大的 net/rpc 库,能够让开发者轻松实现基于 Go 的 RPC 服务。本文将介绍 Go 中 RP…...
挖耳勺可以伸进耳朵多深?安全可视挖耳勺推荐!
一般来说,挖耳勺不应该伸进耳朵太深,外耳道的长度大约在2.5厘米到3.5厘米之间,但不建议将挖耳勺伸进超过外耳道外1/3的深度,也就是大概1厘米左右较为安全。因为如果伸得太深,很容易损伤外耳道皮肤,引起疼痛…...
SuperMap GIS基础产品FAQ集锦(20240911)
一、SuperMap iObjects Java 问题1:【iObject Python】Objects Python产品有哪些能力特性和优势? 11.2.0 【解决办法】iObjects Python产品包含传统GIS功能(基于iObjects Java扩展的功能接口)和AI GIS功能模块。 其中传统GIS功能…...
从状态管理到性能优化:全面解析 Android Compose
文章目录 引言一、Android Compose基本概念1.1 什么是Android Compose?1.2 Compose的优势1.3 如何在项目中使用Compose 二、Compose中的状态管理2.1 状态管理的重要性2.2 Compose中的状态和数据流2.3 使用State和MutableState处理状态2.4 通过ViewModel进行状态管理 三、Compo…...
ChatGPT提示词优化大师使用指南
我希望你成为我的ChatGPT提示词优化大师。 您的目标是帮助我根据自己的需要制定尽可能最好的提示。 你提供的提示应该是站在我向ChatGPT发起请求的角度来写的。我的初始提示词如下:此处填入你的初始提示词 ChatGPT提示词生成器 我希望你充当提示词生成器。 比如&…...
计算机毕业设计 智能推荐旅游平台 Java+SpringBoot+Vue 前后端分离 文档报告 代码讲解 安装调试
🍊作者:计算机编程-吉哥 🍊简介:专业从事JavaWeb程序开发,微信小程序开发,定制化项目、 源码、代码讲解、文档撰写、ppt制作。做自己喜欢的事,生活就是快乐的。 🍊心愿:点…...
【拥抱AI】基于多种数据分段工具的优缺点分析
最近在深入了解RAG方面的知识,其中数据清洗和数据分段是创建知识库的重要步骤。数据清洗目前暂时选用了MinerU,然后就需要针对数据分段进行选型。 以下是我了解到的几种数据分段工具,简单总结了一下它们的优缺点,权当笔记分享&am…...
在 Windows 系统上,文件传输到虚拟机(VM)可以通过 VS Code 的图形界面(GUI)或命令行工具进行操作
在 Windows 系统上,文件传输到虚拟机(VM)可以通过 VS Code 的图形界面(GUI)或命令行工具进行操作。以下是几种方法: ### 方法 1: 使用 VS Code 图形界面 1. **连接到远程 VM**: - 在 VS Cod…...
kafka的主要功能
Apache Kafka 是一个分布式流处理平台,它最初由 LinkedIn 开发,后来捐赠给了 Apache Software Foundation,并成为了 Apache 的顶级项目。Kafka 设计用于处理实时数据流,并且提供了高性能、可扩展性和持久性。下面是 Kafka 的主要功…...
vue3中provide和inject详解
provide和inject是什么 provide 和 inject 是 Vue.js 框架中提供的一种依赖注入机制。这种机制允许一个祖先组件(提供者)向其所有子孙组件(使用者)提供数据或方法,而不需要通过逐层组件传递属性(props&…...
相约华中科技大学,移动云技术论坛来了!NineData创始人CEO叶正盛将分享《数据库全球实时传输技术实践》的主题演讲
2024年9月12日,中国移动云能力中心将在华中科技大学举办“智算浪潮下数据库发展论坛”,共同探讨数据库技术与应用的创新,分享算力网络时代数据库未来发展的洞见。本次论坛,NineData 创始人&CEO 叶正盛受邀参会,并来…...
华为 昇腾 310P 系列 AI 处理器支持 140Tops 的 AI 算力。
1、产品简介 模组是基于昇腾 310P 系列 AI 处理器设计而成,可实现图像、视频等多种数据分析 与推理计算。超强的视频编解码能力以及支持 140Tops 的 AI 算力。在边缘侧及端侧的嵌入式计算 领域,有着极高的性价比,具有超强算力、 超高能效、…...
第19节 Node.js Express 框架
Express 是一个为Node.js设计的web开发框架,它基于nodejs平台。 Express 简介 Express是一个简洁而灵活的node.js Web应用框架, 提供了一系列强大特性帮助你创建各种Web应用,和丰富的HTTP工具。 使用Express可以快速地搭建一个完整功能的网站。 Expre…...
DockerHub与私有镜像仓库在容器化中的应用与管理
哈喽,大家好,我是左手python! Docker Hub的应用与管理 Docker Hub的基本概念与使用方法 Docker Hub是Docker官方提供的一个公共镜像仓库,用户可以在其中找到各种操作系统、软件和应用的镜像。开发者可以通过Docker Hub轻松获取所…...
Spring AI 入门:Java 开发者的生成式 AI 实践之路
一、Spring AI 简介 在人工智能技术快速迭代的今天,Spring AI 作为 Spring 生态系统的新生力量,正在成为 Java 开发者拥抱生成式 AI 的最佳选择。该框架通过模块化设计实现了与主流 AI 服务(如 OpenAI、Anthropic)的无缝对接&…...
06 Deep learning神经网络编程基础 激活函数 --吴恩达
深度学习激活函数详解 一、核心作用 引入非线性:使神经网络可学习复杂模式控制输出范围:如Sigmoid将输出限制在(0,1)梯度传递:影响反向传播的稳定性二、常见类型及数学表达 Sigmoid σ ( x ) = 1 1 +...
【C++从零实现Json-Rpc框架】第六弹 —— 服务端模块划分
一、项目背景回顾 前五弹完成了Json-Rpc协议解析、请求处理、客户端调用等基础模块搭建。 本弹重点聚焦于服务端的模块划分与架构设计,提升代码结构的可维护性与扩展性。 二、服务端模块设计目标 高内聚低耦合:各模块职责清晰,便于独立开发…...
Aspose.PDF 限制绕过方案:Java 字节码技术实战分享(仅供学习)
Aspose.PDF 限制绕过方案:Java 字节码技术实战分享(仅供学习) 一、Aspose.PDF 简介二、说明(⚠️仅供学习与研究使用)三、技术流程总览四、准备工作1. 下载 Jar 包2. Maven 项目依赖配置 五、字节码修改实现代码&#…...
解读《网络安全法》最新修订,把握网络安全新趋势
《网络安全法》自2017年施行以来,在维护网络空间安全方面发挥了重要作用。但随着网络环境的日益复杂,网络攻击、数据泄露等事件频发,现行法律已难以完全适应新的风险挑战。 2025年3月28日,国家网信办会同相关部门起草了《网络安全…...
永磁同步电机无速度算法--基于卡尔曼滤波器的滑模观测器
一、原理介绍 传统滑模观测器采用如下结构: 传统SMO中LPF会带来相位延迟和幅值衰减,并且需要额外的相位补偿。 采用扩展卡尔曼滤波器代替常用低通滤波器(LPF),可以去除高次谐波,并且不用相位补偿就可以获得一个误差较小的转子位…...
【Elasticsearch】Elasticsearch 在大数据生态圈的地位 实践经验
Elasticsearch 在大数据生态圈的地位 & 实践经验 1.Elasticsearch 的优势1.1 Elasticsearch 解决的核心问题1.1.1 传统方案的短板1.1.2 Elasticsearch 的解决方案 1.2 与大数据组件的对比优势1.3 关键优势技术支撑1.4 Elasticsearch 的竞品1.4.1 全文搜索领域1.4.2 日志分析…...
C++实现分布式网络通信框架RPC(2)——rpc发布端
有了上篇文章的项目的基本知识的了解,现在我们就开始构建项目。 目录 一、构建工程目录 二、本地服务发布成RPC服务 2.1理解RPC发布 2.2实现 三、Mprpc框架的基础类设计 3.1框架的初始化类 MprpcApplication 代码实现 3.2读取配置文件类 MprpcConfig 代码实现…...
