luogu P1962 斐波那契数列
(gg直接讲的用矩阵求斐波那契数列
(原地死亡
(全程一脸懵逼
(然后看了半个点题解
首先,什么是矩阵呢
就是类似于这样的东西(里面可以填什么复数啊,实数啊的
然后矩阵的基本运算了解一下
加法很简单emmmm(不说了
乘法需要了解一下,毕竟比较神奇
(A * B != B * A 难道不觉得违背常识吗?多神奇啊!
(我觉得讲矩阵乘法讲的最好,最通俗易懂的是曹天元所著的《上帝掷骰子吗》中 chapter 05 part 3,推荐看一下
矩阵乘法嘛。。。只要知道基本要求就那么求就行了emmmm
两个矩阵,第一个矩阵的列数与第二个矩阵的行数相等时即可相乘
举个栗子
然后正经的解释和公式是酱的:
设A为 m * p 的矩阵,B为 p * n 的矩阵,那么称 m * n 的矩阵C为矩阵A与B的乘积,记作 C = AB
其中矩阵C中的第 i 行第 j 列元素可以表示为
需要注意的是
(来源百度百科【特别鸣谢orz
大概理解了矩阵乘法之后我们来看看这道题吧
标签是矩阵乘法诶那怎么用呢【考场上能想到矩阵乘法的都tql!!!
一看数据范围,显然正常递推会只得60分
如果想要拿到满分需要想一下优化
然后我们刚刚说到矩阵
(我也不知道他们怎么想出来用矩阵的 tql!!!
我们会发现矩阵的定义里有这么一个东西叫做单位矩阵
主对角线上的元素都为1,其余元素全为0的n阶矩阵称为n阶单位矩阵
(主对角线就是左上角到右下角的那条对角线
它长这个样子
它有什么用呢?
所有矩阵乘上单位矩阵都等于本身
(哇看起来好鸡肋23333
(说实话我也不知道它有什么用
(但是它给我们提供了一个思路,如何模拟斐波那契数列
如果我们构造一个矩阵(符合斐波那契数列的规律
我们要推出它从何而来
因为我们知道 F [i] = F [i - 1] + F [i - 2]
那么某两个矩阵相乘能够得到这样一个矩阵
因为我们要找规律嘛,所以其中一个矩阵一定与构造的那个矩阵性质相似
即为
那再逆着推出来另一个矩阵就很简单了
最后得到
这样一直推下去
一定会推到 i = 2 ,i - 1 = 1
这样的话定义一个初始矩阵两行全为一,再反复乘这个固定的
矩阵
就能得到最终的结果
因为最初的 F [1],F [2]已经定义了
所以要求出F [n]的值,我们只需要乘上固定矩阵的 n - 2次方即可
这里需要用到矩阵快速幂
其实和快速幂没什么区别,只是需要写一个矩阵相乘的函数或是重置运算符
但是一定要记住,因为矩阵相乘 A * B != B * A
所以如果初始矩阵与固定矩阵乘反了的话,结果就不一样了
如果反过来,初始矩阵就应该是一行两列的矩阵了
(我就是这样写的23333
最后的结果就是第一行第一列的数了
看代码吧~
#include<cstdio> #include<cstring> #define ll long long #define mod 1000000007//别忘了膜 using namespace std;struct matrix {ll a[3][3];matrix() {memset(a,0,sizeof(a));} } ans,base;//用结构体存放矩阵,并在结构体中将数组一次性初始化 matrix operator * (const matrix &x,const matrix &y) {matrix z;for(ll i = 1; i <= 2; i++)for(ll j = 1; j <= 2; j++)for(ll k = 1; k <= 2; k++)z.a[i][j] = (z.a[i][j] + x.a[i][k] * y.a[k][j] % mod) % mod;return z; }//重置运算符,不然写个函数也行void quickpow(ll b) {while(b) {if(b & 1) ans = ans * base;//别乘反了base = base * base;b >>= 1;} }//快速幂int main() {ll n;scanf("%lld",&n);if(n <= 2) {printf("1");return 0;}base.a[1][1] = base.a[1][2] = base.a[2][1] = 1;//固定矩阵ans.a[1][1] = ans.a[1][2] = 1;//初始矩阵quickpow(n - 2);printf("%lld",ans.a[1][1] % mod);return 0; }
emmmmm
那么这道题就讲完啦
第二道蓝题祭~
转载于:https://www.cnblogs.com/sevenyuanluo/p/10041378.html
luogu P1962 斐波那契数列相关推荐
- 洛谷P1962 斐波那契数列题解
题目背景 大家都知道,斐波那契数列是满足如下性质的一个数列: • f(1) = 1 • f(2) = 1 • f(n) = f(n-1) + f(n-2) (n ≥ 2 且 n 为整数) 题目描述 请 ...
- 洛谷P1962 斐波那契数列
传送门 不难得到状态转移矩阵 然后带进去乱搞 1 //minamoto 2 #include<iostream> 3 #include<cstdio> 4 #include&l ...
- 求斐波那契数列的第n项
提要 本文介绍了4种(3种?)求斐波那契数列第n项的方法. 斐波那契数列简介 斐波那契数列(Fibonacci sequence),又称黄金分割数列.因数学家列昂纳多·斐波那契(Leonardoda ...
- 斐波那契数列的前n项值
Description 输入n,求斐波那契数列前n项的值.斐波那契数列规律如下:1, 1, 2, 3, 5, 8, 13,21, 34,55-,从第三项开始,每一项都是前面两项的和. Input 输入 ...
- P1720 月落乌啼算钱(斐波那契数列)--python3实现
https://www.luogu.com.cn/problem/P1720 """P1720 月落乌啼算钱(斐波那契数列) https://www.luogu.com. ...
- java 斐波拉_Java实现斐波那契数列
斐波纳契数列,又称黄金分割数列,指的是这样一个数列:1.1.2.3.5.8.13.21.--在数学上,斐波纳契数列以如下被以递归的方法定义:F0=0,F1=1,Fn=F(n-1)+F(n-2)(n&g ...
- 剑指offer:面试题10- I. 斐波那契数列
写一个函数,输入 n ,求斐波那契(Fibonacci)数列的第 n 项.斐波那契数列的定义如下: F(0) = 0, F(1) = 1 F(N) = F(N - 1) + F(N - 2), 其中 ...
- 用递归法计算斐波那契数列的第n项
斐波纳契数列(Fibonacci Sequence)又称黄金分割数列,指的是这样一个数列:1.1.2.3.5.8.13.21.--在数学上,斐波纳契数列以如下被以递归的方法定义:F0=0,F1=1, ...
- 循环斐波那契数列_剑指offer #10 斐波那契数列
(递归和循环)#10 斐波那契数列 一.斐波那契数列 定义: n = 0 , f(n) = 0 n = 1 , f(n) = 1 n > 1 , f(n) = f(n-1) + f(n-2) 思 ...
最新文章
- 设计模式入门:建造者模式
- Python命令行补全设置
- Java基础-锁机制
- Android selector
- 安卓布局工具---Hierarchy Viewer
- Unity网格合并_材质合并[转]
- 十四个值得推荐的个人提升方法
- powershell 学习地址
- XCTF-高手进阶区:web2
- mcq 队列_MCQ | 基础知识 免费和开源软件| 套装3
- 效果好,速度快!大连海事大学提出基于增强多任务学习的单图像去雨算法MENET...
- 【MySQL】小表驱动大表
- 车牌识别算法介绍与实践(转)
- 使用FileWriter向文本文件中写信息
- python 获取excel文本框_python学习-excel读取
- vscode可以配置哪些编程语言_vscode支持哪些编程语言
- 剑桥口语 — 48 个音标标准口型与细节发音
- oracle11g ora12170,11g告警日志中大量ORA-12170错误
- mc服务器tps优化,[教程] 使用Openj9大幅降低MC的内存占用,提高FPS和TPS
- php stomp rabbitmq,rabbitmq-web-stomp 优化过程