[矩阵快速幂] 数列(类斐波那契

数列

题目描述

a[1]=a[2]=a[3]=1

a[x]=a[x-3]+a[x-1]

求a数列的第n项对1000000007(10^9+7)取余的值。

输入

第一行一个整数T,表示询问个数。

以下T行,每行一个正整数n。

输出

每行输出一个非负整数表示答案。

样例输入

3
6
8
10

样例输出

4
9
19

提示

对于30%的数据 n<=100;

对于60%的数据 n<=2*10^7;

对于100%的数据 T<=100,n<=2*10^9;

emmm基本就是一道矩阵快速幂的裸题,根据题目需要自己求得矩阵套进去即可

(顺便一提,学校OJ里输出1的情况没有换行竟然只有18分orz  调试了半天不知道错在哪里

下面放上代码

 1 #include<cstdio>
 2 #include<cstring>
 3
 4 const int Mod = 1e9 + 7;
 5
 6 struct Matrix {
 7     long long m[3][3];
 8 };
 9
10 Matrix Mult(Matrix a, Matrix b) {
11     long long sums = 0;
12     Matrix c;
13     memset(c.m, 0, sizeof(c.m));
14     for (int i = 0; i <= 2; i++) {
15         for (int j = 0; j <= 2; j++) {
16             sums = 0;
17             for (int k = 0; k <= 2; k++) {
18                 sums = (sums + a.m[i][k] * b.m[k][j]) % Mod;
19             }
20             c.m[i][j] = sums;
21         }
22     }
23     return c;
24 }
25
26 Matrix Qpow(Matrix a, int k) {
27     Matrix res;
28     memset(res.m, 0, sizeof(res.m));
29     for (int i = 0; i <= 2; i++) {
30         res.m[i][i] = 1;
31     }
32     while(k) {
33         if (k & 1) {
34             res = Mult(res, a);
35         }
36         a = Mult(a, a);
37         k = (k >> 1);
38     }
39     return res;
40 }
41
42 int main() {
43     long long n;
44     int t;
45     scanf("%d", &t);
46     for (int cnt = 1; cnt <= t; cnt++) {
47         Matrix A, B;
48         memset(A.m, 0, sizeof(A.m));
49         memset(B.m, 0, sizeof(B.m));
50         scanf("%lld", &n);
51         if (n <= 3) {
52             printf("1\n");
53             continue;
54         }
55         for (int i = 0; i < 3; i++) {
56             A.m[i][i + 1] = 1;
57         }
58         A.m[2][0] = 1;
59         A.m[2][2] = 1;
60         for (int i = 0; i < 3; i++) {
61             B.m[i][0] = 1;
62         }
63         A = Qpow(A, n - 3);
64         A = Mult(A, B);
65         printf("%d\n", A.m[2][0]);
66     }
67     return 0;
68 }

原文地址:https://www.cnblogs.com/GldHkkowo/p/8832843.html

时间: 2024-10-12 09:20:54

[矩阵快速幂] 数列(类斐波那契的相关文章

【斐波那契】【矩阵快速幂模板】斐波那契公约数

这道题求第n项和第m项斐波那契的公约数这里有一个定理(n,m都是1e9) gcd(f[m],f[n])=f[gcd(n,m)] 斐波那契使用矩阵快速幂求 #include <bits/stdc++.h> #define ll long long #define ull unsigned long long #define ld long double using namespace std; const int maxn=20010; const int NIL=0; const int mo

斐波那契数列以及斐波那契数列的衍生形式 利用矩阵快速幂求解

一.斐波那契数列F[n]=F[n-1]+F[n-2] 可转换为矩阵s[1,1,1,0]的n次幂的矩阵的s[0][1]的值 矩阵的幂次方 可通过 奇判断及进制移位提高时间效率 位与运算 n&1表示的意思:取二进制n的最末位,二进制的最末位为零表示n为哦数,为1表示奇数,即等价于n%2 n>>1 是将n的二进制向右移动一位, n>>=1 即把移动后的值赋给n 题目:求斐波那契数列F[n]%10000(取模) #include <cstdio> #include &l

类 斐波那契

class Fab(object): def __init__(self,max): self.max = max self.n ,self.a ,self.b = 0 ,0 ,1 def __iter__(self): #继承object,重写__iter__后,自动调用__next__方法,返回r对象 return self def __next__(self): #此处python2为next,python3为__next__,注意区别 if self.b <= self.max: r =

一些特殊的矩阵快速幂 hdu5950 hdu3369 hdu 3483

思想启发来自, 罗博士的根据递推公式构造系数矩阵用于快速幂 对于矩阵乘法和矩阵快速幂就不多重复了,网上很多博客都有讲解.主要来学习一下系数矩阵的构造 一开始,最一般的矩阵快速幂,要斐波那契数列Fn=Fn-1+Fn-2的第n项,想必都知道可以构造矩阵来转移 其中,前面那个矩阵就叫做系数矩阵(我比较喜欢叫转移矩阵) POJ3070 Fibonacci 可以试一试 1 #include<cstdio> 2 typedef long long ll; 3 const ll md=10000; 4 st

hdu--4549 M斐波那契数列

Problem Description M斐波那契数列F[n]是一种整数数列,它的定义如下: F[0] = aF[1] = bF[n] = F[n-1] * F[n-2] ( n > 1 ) 现在给出a, b, n,你能求出F[n]的值吗? Input 输入包含多组测试数据:每组数据占一行,包含3个整数a, b, n( 0 <= a, b, n <= 10^9 ) Output 对每组测试数据请输出一个整数F[n],由于F[n]可能很大,你只需输出F[n]对1000000007取模后的值

A - Number Sequence(矩阵快速幂或者找周期)

Description A number sequence is defined as follows: f(1) = 1, f(2) = 1, f(n) = (A * f(n - 1) + B * f(n - 2)) mod 7. Given A, B, and n, you are to calculate the value of f(n). Input The input consists of multiple test cases. Each test case contains 3

FZU 1911 Construct a Matrix ( 矩阵快速幂 + 构造 )

FZU 1911 Construct a Matrix (  矩阵快速幂 + 构造 ) 题意: 需要构造一个矩阵满足如下要求: 1.矩阵是一个S(N)*S(N)的方阵 2.S(N)代表斐波那契数列的前N项和模上M 3.矩阵只能由1, 0, -1组成 4.矩阵每行每列的和不能相等 Here, the Fibonacci numbers are the numbers in the following sequence: 1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 89, 1

HDU5171 矩阵快速幂

题目描述:http://acm.hdu.edu.cn/showproblem.php?pid=5171 算法: 可以先将数组a[]排序,然后序列 a1 , a2 , … , an 即为有序序列,则第一次加入的就是 an + an-1 ,第二次就是 an + (an + an-1) ,如此循环就构成了斐波那契序列. 设斐波那契序列的第k项为Fk,则可知第k次加入的即为 Fk+1 * an +  Fk * an-1 设斐波那契序列的前k项和为Sk, 则所得结果res即为:a1 + a2 + … +

[洛谷1962]斐波那契数列

思路: 常见算法时矩阵快速幂,但事实上这题可以不需要矩阵快速幂. 设斐波那契数列为$f$,观察规律可以发现: 当$n$为偶数时,$f_n=(f_{n-1}\times 2+f_n)\times f_n$: 当$m$为奇数时,$f_n=f_{n+1}^2+f_n^2$. 这样只要用一个map记录已经计算过的Fibonacci数,递归求得答案即可. 再用一个hash_map跑得和标算一样快(0ms),而且内存更小. 1 #include<cstdio> 2 #include<ext/hash