[C/C++入门][for]24、菲波那契数列

斐波那契数列是数学中的一个经典数列,以其独特的递归性质而闻名。

数列的前两项通常是0和1(或者有时从1开始,当然这个不是强制要求),之后的每一项都是前两项的和。数列的前几项如下所示:

0, 1, 1, 2, 3, 5, 8, 13, 21, 34, ......

斐波那契数列在自然界、艺术、建筑以及金融领域都有广泛的体现和应用,它还与黄金分割比例有关联。

我们可以用按照这个规律来实现斐波那契数列的计算——步骤:

  1. 初始化

    确定迭代的起始条件。对于斐波那契数列,前两项分别为F(0)=0和F(1)=1,所以需要初始化两个变量,分别代表当前项和前一项。
  2. 设定循环

    设定一个循环结构,从初始状态开始,逐步向目标状态推进。对于求解第n项,循环的次数应当是从2到n。
  3. 更新状态

    在每一次循环中,根据当前的状态计算新的状态。对于斐波那契数列,就是将前两项相加得到当前项。更新变量,将当前项赋值给前一项,将新计算出的当前项赋值给当前项变量。
  4. 终止条件

    循环应该有一个明确的终止条件。对于求解第n项,当循环计数器达到n时,循环结束。
  5. 返回结果

    当循环结束后,最后一个计算出的当前项即为所求的斐波那契数列的第n项。
#include <iostream>
using namespace std;unsigned long fibonacci(unsigned int n) {// Step 1: 初始化if (n <= 1) return n;unsigned long prev = 0, curr = 1;// Step 2: 设定循环for (unsigned int i = 2; i <= n; ++i) {// Step 3: 更新状态unsigned long next = prev + curr;prev = curr;curr = next;}// Step 5: 返回结果return curr;
}int main() {unsigned int n;cout << "请输入想要求解的斐波那契数列的项数:";cin >> n;cout << "斐波那契数列的第" << n << "项是:" << fibonacci(n) << endl;return 0;
}

 这是一种非常常见的方法。还有比如递归,动态规划等。可以作为了解。

(扩展)递归

斐波那契数列定义为:F(0) = 0, F(1) = 1, F(n) = F(n-1) + F(n-2) (n > 1)。

unsigned long fibonacci_recursive(unsigned int n) {if (n <= 1) // 基本情况return n;else // 递归情况return fibonacci_recursive(n - 1) + fibonacci_recursive(n - 2);
}

只要从高到底不断加就可以。

(扩展)动态规划

动态规划是一种优化的递归方法,主要针对那些具有重叠问题和最优子结构特征的问题。

它通过存储子问题的解来避免重复计算,从而大大提高了效率。

动态规划有两种主要形式:自底向上自顶向下带备忘录(记忆功能)。

  • 自底向上:从最小的子问题开始,逐步构建到最终的解。
  • 自顶向下带备忘录:从大问题开始,遇到已解决的子问题就直接使用其解,避免重复计算。
unsigned long fibonacci_dp(unsigned int n) {if (n <= 1)return n;unsigned long fib[n+1];fib[0] = 0;fib[1] = 1;for (unsigned int i = 2; i <= n; i++) {fib[i] = fib[i-1] + fib[i-2];}return fib[n];
}

(扩展)结合递归和动态规划的一种效率高的方法。

unsigned long fibonacci_memo(unsigned int n, unsigned long memo[]) {if (memo[n] != -1)return memo[n];if (n <= 1)memo[n] = n;elsememo[n] = fibonacci_memo(n-1, memo) + fibonacci_memo(n-2, memo);return memo[n];
}unsigned long fibonacci_memo_topdown(unsigned int n) {unsigned long memo[n+1];for (unsigned int i = 0; i <= n; i++)memo[i] = -1;return fibonacci_memo(n, memo);
}

这是一种结合了递归与动态规划优点的技术。这种方法的核心思想是在递归的过程中,对已经计算过的结果进行缓存,这样当下次需要同样的结果时,就可以直接从缓存中读取,而不需要重新计算,这极大地提升了效率,尤其是在处理具有大量重复子问题的情况时。

让我们再次以斐波那契数列为例来深入解释这一过程:

假设我们想要计算F(n),即第n个斐波那契数。按照递归的思路,我们会首先尝试计算F(n-1)F(n-2),然后将这两个结果相加得到F(n)。但是,在计算F(n-1)F(n-2)的过程中,我们又会遇到更多的子问题,比如F(n-2)F(n-3)等等。如果我们不采取任何措施,那么对于F(n-2),我们会在计算F(n-1)F(n)时重复计算两次。

步骤解析:

  1. 初始化备忘录:创建一个数组或哈希表作为备忘录,用于存储之前计算过的子问题的答案。通常,我们初始化所有值为-1或某个特殊标记,表示这些值尚未被计算。

  2. 递归计算

    • 当我们需要计算某个子问题F(i)时,首先检查备忘录中是否已经有了F(i)的结果。
    • 如果有,直接返回该结果;如果没有,按照递归公式计算F(i),并将结果存入备忘录中。
  3. 返回最终结果:当递归到达基本情况时,直接返回结果,否则返回备忘录中存储的计算结果。

代码实现带注释:

unsigned long fibonacci_memo(unsigned int n, unsigned long memo[]) {// 如果结果已经计算过,直接返回if (memo[n] != -1)return memo[n];// 基本情况if (n <= 1)memo[n] = n;else {// 计算并存储结果memo[n] = fibonacci_memo(n-1, memo) + fibonacci_memo(n-2, memo);}// 返回计算结果return memo[n];
}unsigned long fibonacci_memo_topdown(unsigned int n) {unsigned long memo[n+1];// 初始化备忘录for (unsigned int i = 0; i <= n; i++)memo[i] = -1;// 开始递归计算return fibonacci_memo(n, memo);
}

这个理解稍微会难一点,初学者可能理解不了。我们可以作为扩展阅读,等后面学到这我们回来再看这个问题。

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

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

相关文章

docker网络互联

最近学习docker的时候发现多了很多网卡&#xff0c;这些似乎都和docker有关&#xff0c;所以我便往下深入了解了一番&#xff1b; 一、docker网卡 docker 0是安装 docker 的时候生成的虚拟网桥&#xff0c;它在内核层连通了其他物理或者虚拟网卡&#xff0c;这就可以将所…

AI发展下的伦理挑战,应当如何应对?

AI发展下的伦理挑战&#xff0c;应当如何应对&#xff1f; 人工智能飞速发展的同时&#xff0c;也逐渐暴露出侵犯数据隐私、制造“信息茧房”等种种伦理风险。随着AI技术在社会各个领域的广泛应用&#xff0c;关于AI伦理和隐私保护问题日趋凸显。尽管国外已出台系列法规来规范…

常用优秀内网穿透工具(实测详细版)

文章目录 1、前言2、安装Nginx3、配置Nginx4、启动Nginx服务4.1、配置登录页面 5、内网穿透5.1、cpolar5.1.1、cpolar软件安装5.1.2、cpolar穿透 5.2、Ngrok5.2.1、Ngrok安装5.2.2、随机域名5.2.3、固定域名5.2.4、前后端服务端口 5.3、NatApp5.4、Frp5.4.1、下载Frp5.4.2、暴露…

自动发卡机器人来看:生成式AI的未来,是聊天还是代理?

引言 今天我们要聊聊一个有趣的话题&#xff1a;生成式AI的未来究竟是在聊天系统&#xff08;Chat&#xff09;中展现智慧&#xff0c;还是在自主代理&#xff08;Agent&#xff09;中体现能力&#xff1f; 一、生成式AI&#xff0c;你是谁&#xff1f; 首先&#xff0c;生成…

【数据结构】--- 栈和队列

前言 前面学习了数据结构的顺序表、单链表、双向循环链表这些结构&#xff1b;现在就来学习栈和队列&#xff0c;这里可以简单的说栈和队列是具有特殊化的线性表 一、栈 1.1、栈的概念和结构 栈是一种遵循先入后出逻辑的线性数据结构。 栈是一种特殊的线性表&#xff0c;它只允…

vivado FFT IP Core

文章目录 前言FFT IP 接口介绍接口简介tdata 格式说明 其他细节关于计算精度及缩放系数计算溢出架构选择数据顺序实时/非实时模式数据输入输出时序关于配置信息的应用时间节点 FFT IP 例化介绍控制代码实现 & 测试参考文献 前言 由于计算资源受限&#xff0c;准备将上位机 …

【漏洞复现】泛微E-Cology WorkflowServiceXml SQL注入漏洞

0x01 产品简介 泛微e-cology是一款由泛微网络科技开发的协同管理平台&#xff0c;支持人力资源、财务、行政等多功能管理和移动办公。 0x02 漏洞概述 泛微OAE-Cology 接口/services/WorkflowServiceXml 存在SQL注入漏洞&#xff0c;可获取数据库权限&#xff0c;导致数据泄露…

Qt日志库QsLog使用教程

前言 最近项目中需要用到日志库。上一次项目中用到了log4qt库&#xff0c;这个库有个麻烦的点是要配置config文件&#xff0c;所以这次切换到了QsLog。用了后这个库的感受是&#xff0c;比较轻量级&#xff0c;嘎嘎好用&#xff0c;推荐一波。 下载QsLog库 https://github.c…

【踩坑日记】【教程】嵌入式 Linux 通过 nfs 下载出现 T T T T [Retry count exceeded: starting again]

文章目录 1 本篇文章解决的问题2 问题解决原理3 问题环境4 开启 ubuntu-20.04 的 nfs24.1 确认 nfs2 是否已经开启4.2 开启 nfs2 5 卸载 iptables5.1 卸载 iptables5.2 禁用 ufw5.3 尝试重新下载 6 原理分析6.1 nfs2 开启部分6.2 卸载 iptables 部分 7 后记7.1 拓扑结构一7.2 拓…

生成Elasticsearch xpack安全认证证书

首次启动 Elasticsearch 时&#xff0c;会为用户生成密码&#xff0c;并自动为用户配置 TLS &#xff0c;可以随时调整 TLS 配置&#xff0c;更新节点证书 一、生成证书 1、在任意节点上进入 Elasticsearch 的安装目录&#xff0c;使用 elasticsearch-certutil 为集群生成 CA…

【博士每天一篇文献-算法】连续学习算法之HNet:Continual learning with hypernetworks

阅读时间&#xff1a;2023-12-26 1 介绍 年份&#xff1a;2019 作者&#xff1a;Johannes von Oswald&#xff0c;Google Research&#xff1b;Christian Henning&#xff0c;EthonAI AG&#xff1b;Benjamin F. Grewe&#xff0c;苏黎世联邦理工学院神经信息学研究所 期刊&a…

npm 设置镜像

设置淘宝源 npm config set registry https://registry.npmmirror.com 设置阿里云源 npm config set registry https://npm.aliyun.com 设置腾讯云源 npm config set registry https://mirrors.cloud.tencent.com/npm/ 设置华为云源 npm config set registry https://mi…

嘿!openlayer(三)

嘿&#xff01;openlayer&#xff08;三&#xff09; 第三章 面向对象的openlayer 文章目录 嘿&#xff01;openlayer&#xff08;三&#xff09;前言一、面向对象的openlayer核心类渲染类事件类openlayer 主要工作原理数据组织数据解析数据渲染 二、直击深处OpenLayers 内部生…

【Vue3 ts】echars图表展示统计的月份数据

图片展示 此处内容为展示24年各个月份产品的创建数量。在后端统计24年各个月份产品数量后&#xff0c;以数组的格式发送给前端&#xff0c;前端负责展示。 后端 entity层&#xff1a; Data Schema(description "月份统计")public class MonthCount {private Stri…

处理uniapp刷新后,点击返回按钮跳转到登录页的问题

在使用uniapp的原生返回的按钮时&#xff0c;如果没有刷新会正常返回到对应的页面&#xff0c;如果刷新后会在当前页反复横跳&#xff0c;或者跳转到登录页。那个时候我第一个想法时&#xff1a;使用浏览器的history.back()方法。因为浏览器刷新后还是可以通过右上角的返回按钮…

01认识Java(介绍安装调试)

单元概述 本章主要介绍Java语言的发展历史&#xff0c;了解Java的运行原理及Java编程语言的特点&#xff0c;通过搭建Eclipse集成开发环境来运行Java应用程序。 1.1 Java简介 1.1.1 什么是Java 计算机语言是人与计算机之间的通讯语言&#xff0c;分为机器语言、汇编语言、高…

短视频是如何一步步“蚕食”我们大脑的?

点击上方△腾阳 关注 转载请联系授权 你好&#xff0c;我是腾阳。 今天我们将深入探讨短视频是如何「蚕食」我们的大脑。 首先问下自己&#xff0c;你有多久没有看完一篇长文了&#xff1f; 你是否曾在清晨阳光中&#xff0c;被手机屏幕上短视频图标吸引&#xff0c;而忘记…

ArrayList.subList的踩坑

需求描述&#xff1a;跳过list中的第一个元素&#xff0c;获取list中的其他元素 原始代码如下&#xff1a; List<FddxxEnterpriseVerify> companyList fddxxEnterpriseVerifyMapper.selectList(companyQueryWrapper);log.info("获取多个法大大公司数据量为&#…

Qt篇——QSqlQueryModel内容居中显示

QSqlQueryModel 本身不提供直接的内容居中显示功能。要实现这一功能&#xff0c;你需要子类化 QSqlQueryModel 并重新实现数据显示的部分。 代码如下&#xff1a; #include <QSqlQueryModel> #include <QVariant>class CenteredSqlQueryModel : public QSqlQueryM…

【Vue】快速入门:构建你的第一个Vue 3应用

文章目录 一、Vue简介二、环境搭建1. 安装Node.js和npm2. 安装Vue CLI 三、创建Vue项目四、项目结构介绍五、组件基础创建一个组件使用组件 六、模板语法插值指令v-bindv-ifv-for 七、事件处理八、状态管理安装Vuex创建Store使用Store 九、路由基础安装Vue Router配置路由使用路…