36-递归与迭代

36-1 用递归和迭代解决问题

1、求n的阶乘

公式:

n!=1×2×3×...×(n-1)×n。用递归方式定义:0!=1,n!=(n-1)!×n。

代码1:

我们先回忆一下之前用循环怎么实现的吧

非递归,也可称迭代

int main()
{int n = 0;scanf("%d", &n);int i = 1;int ret = 1;for (i = 1; i <= n; i++){ret = i * ret;}printf("%d\n", ret);return 0;
}

运行结果:

代码2:

递归

int fac(num)
{if (num > 1){return num * fac(num - 1);}else{return 1;}
}
int main()
{int n = 0;scanf("%d", &n);int ret = fac(n);printf("%d\n", ret);return 0;
}

运行结果:

有些时候,并不适合用递归

2、求第n个斐波那契数

斐波那契数列:在数学上,斐波那契数列可以通过递推的方式定义,从第三项开始,每一项都等于前两项之和。具体的递推公式为F(0)=0,F(1)=1,F(n)=F(n-1)+F(n-2),其中n≥2且n属于自然数集。

代码1:递归方法

int F(n)
{int ret = 0;if (n >= 2){return F(n - 1) + F(n - 2);}else if (0 == n){return 0;}else{return 1;}
}
int main()
{int n = 0;scanf("%d", &n);int ret = F(n);printf("%d\n", ret);return 0;
}

 运行结果:

但是,这里会有大量重复的计算!严重浪费时间

我们可以进行一个测试

int count = 0;  //计数器
int F(n)
{int ret = 0;if (n == 3){count++;  //计数,一共算了多少次第三个斐波那契数}if (n >= 2){return F(n - 1) + F(n - 2);}else if (0 == n){return 0;}else{return 1;}
}
int main()
{int n = 0;scanf("%d", &n);int ret = F(n);printf("%d\n", ret);printf("count=%d\n", count);return 0;
}

运行结果:

竟然算了将近4万次!!!

效率太低了,用递归太不合适啦!我们试试迭代吧~~~

代码2:迭代

①for循环

int Fib(n)
{if (n >= 2){int sum = 0;int i = 0;int n1 = 1;  //第一个数int n2 = 1;  //第二个数for (i = 0; i < n-2; i++)  //直接从第3个算起{sum = n1 + n2;n1 = n2;n2 = sum;}return sum;}else if(0==n){return 0;}else{return 1;}
}
int main()
{int n = 0;scanf("%d", &n);int ret = Fib(n);printf("%d\n", ret);
}

②while循环(该代码默认n>=1)

int Fib(n)
{int n1 = 1;int n2 = 1;int n3 = 1;while (n >= 3){n3 = n1 + n2;n1 = n2;n2 = n3;n--;}return n3;
}
int main()
{int n = 0;scanf("%d", &n);int ret = Fib(n);printf("%d\n", ret);
}

再使用这两个代码进行测试,你会发现代码运行速度明显比递归的速度快

注意:如果用特别大的数测试,可能会得到负值,这是因为溢出了,关于溢出的问题这里不进行展开

36-2 权衡递归与迭代的使用

1、许多问题是以递归的形式进行解释的,这只是因为它比非递归的形式更为清晰。

2、但是这些问题的迭代实现往往比递归实现效率更高,虽然代码的可读性稍微差些。

3、当一个问题相当复杂,难以用迭代实现时,此时递归实现的简洁性便可以补偿它所带来的运行时开销。

4、如果使用递归没有出现明显的问题,递归可以使用;但是如果有类似的明显问题,则采用非递归的方法解决。

5、递归的层次太深,会出现栈溢出的现象。

应对策略:

①将递归改写成非递归

②使用static对象替代nonstatic局部对象。在递归函数设计中,可以使用static对象替代nonstatic局部对象(即栈对象),这不仅可以减少每次递归调用和返回时产生和释放nonstatic对象的开销,而且static对象还可以保存递归调用的中间状态,并且可为各个调用层所访问。

当然,这只是一些可能的解决方案,并不一定真的能够解决栈溢出的问题

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

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

相关文章

书生浦语训练营2期-第一节课笔记

笔记总结: 了解大模型的发展方向、本质、以及新一代数据清洗过滤技术、从模型到应用的典型流程、获取数据集的网站、不同微调方式的使用场景和训练数据是什么&#xff0c;以及预训练和微调在训练优势、通信/计算调度、显存管理上的区别。 收获&#xff1a; 理清了预训练和微调…

Laya1.8.4 UI长按选择对应位置释放技能

需求&#xff1a; 需要实现拖拽摇杆选择技能释放位置&#xff0c;释放技能。 原理&#xff1a;首先拆分需求&#xff0c;分为两部分&#xff0c;UI部分和场景部分&#xff0c;UI部分需要实现长按效果&#xff0c;长按后又要有拖动效果&#xff0c;将官方文档的示例代码改了改…

[机器学习]练习KNN算法-曼哈顿距离

曼哈顿距离(Manhattan distance) 曼哈顿距离是指在几何空间中两点之间的距离&#xff0c;其计算方法是通过将两点在各个坐标轴上的差值的绝对值相加得到。在二维空间中&#xff0c;曼哈顿距离可以表示为两点在横纵坐标上的差值的绝对值之和&#xff1b;在三维空间中&#xff0…

第十五届蓝桥杯第三期模拟赛第十题 ← 上楼梯

【问题描述】 小蓝要上一个楼梯&#xff0c;楼梯共有 n 级台阶&#xff08;即小蓝总共要走 n 级&#xff09;。小蓝每一步可以走 a 级、b 级或 c 级台阶。 请问小蓝总共有多少种方案能正好走到楼梯顶端&#xff1f;【输入格式】 输入的第一行包含一个整数 n 。 第二行包含三个整…

鸿蒙OS开发实战:【Socket小试MQTT连接】

本篇分享一下 HarmonyOS 中的Socket使用方法 将从2个方面实践&#xff1a; HarmonyOS 手机应用连接PC端 SocketServerHarmonyOS 手机应用连接MQTT 服务端 通过循序渐进的方式&#xff0c;全面了解实践HarmonyOS中的Socket用法 学习本章前先熟悉文档开发知识更新库gitee.com…

马蹄集第九周

MT3011 代码 #include<bits/stdc.h> using namespace std; const int N 1e3 7;int n; struct NODE{vector<int> v;int ind 0; }g[N];int main( ) {cin >> n;int x;for(int i 1; i < n; i){for(int j 1; j< n-1; j){cin >> x;g[i].v.push_…

笔迹/签名数据集汇总

这里只收集公开/易申请的数据集 数据集发表年份语言最小单元Writers/人规模颜色最小单元文件格式示例图片备注CSAFE Handwriting Database2019英语页9090 人*(3 次*9 个样本) 2430 页300 dpi 扫描png-HWDB2.0-2.22011汉字页1,019每人 5 页,共 5091 页灰度图dgrl-CEDAR2006英语…

【python】flask各种版本的项目,终端命令运行方式的实现

✨✨ 欢迎大家来到景天科技苑✨✨ &#x1f388;&#x1f388; 养成好习惯&#xff0c;先赞后看哦~&#x1f388;&#x1f388; &#x1f3c6; 作者简介&#xff1a;景天科技苑 &#x1f3c6;《头衔》&#xff1a;大厂架构师&#xff0c;华为云开发者社区专家博主&#xff0c;…

HEVC的Profile和Level介绍

文章目录 HEVCProfile&#xff08;配置&#xff09;&#xff1a;Level&#xff08;级别&#xff09;&#xff1a;划分标准 HEVC HEVC&#xff08;High Efficiency Video Coding&#xff09;&#xff0c;也称为H.265&#xff0c;是一种视频压缩标准&#xff0c;旨在提供比先前的…

vivado 器件编程

生成器件镜像后 &#xff0c; 下一步是将其下载到目标器件。 Vivado IDE 具有内置原生的系统内器件编程功能用于执行此操作。 Vivado Design Suite 和 Vivado Lab Edition 都包含相应的功能 &#xff0c; 支持您连接到包含 1 个或多个 FPGA 或 ACAP 的硬 件&#xff0c; 以…

数据可视化为什么能在智慧港口中发挥作用?

随着全球贸易活动日益频繁&#xff0c;港口作为国际贸易的重要节点&#xff0c;其运营效率与智能化程度直接影响着整个物流链的效能。在此背景下&#xff0c;智慧港口的概念应运而生&#xff0c;它借助先进的信息技术手段对传统港口进行改造升级&#xff0c;其中&#xff0c;数…

Antd Vue3 使用 Anchor 锚点组件记录

项目场景 客户要求做一个表单页面&#xff0c;表单数据分为三步&#xff0c;每一步骤是一个单独的 Vue 组件&#xff0c;表单上方需要使用锚点组件实现锚点定位到每一步的功能。 代码总览 <template><div class"guided-form-content-wrapper"><!-- …