Gauss Fibonacci

Time Limit: 1000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)
Total Submission(s): 3149    Accepted Submission(s): 1323

Problem Description
Without
expecting, Angel replied quickly.She says: "I'v heard that you'r a very
clever boy. So if you wanna me be your GF, you should solve the problem
called GF~. "
How good an opportunity that Gardon can not give up! The "Problem GF" told by Angel is actually "Gauss Fibonacci".
As
we know ,Gauss is the famous mathematician who worked out the sum from 1
to 100 very quickly, and Fibonacci is the crazy man who invented some
numbers.

Arithmetic progression:
g(i)=k*i+b;
We assume k and b are both non-nagetive integers.

Fibonacci Numbers:
f(0)=0
f(1)=1
f(n)=f(n-1)+f(n-2) (n>=2)

The Gauss Fibonacci problem is described as follows:
Given k,b,n ,calculate the sum of every f(g(i)) for 0<=i<n
The answer may be very large, so you should divide this answer by M and just output the remainder instead.

 
Input
The input contains serveral lines. For each line there are four non-nagetive integers: k,b,n,M
Each of them will not exceed 1,000,000,000.
 
Output
For each line input, out the value described above.
 
Sample Input
2 1 4 100
2 0 4 100
 
Sample Output
21 12
 
这个题要利用的东西挺多的。刚开始连斐波拉契的矩阵都弄错了,看来还是要加强训练!

把斐波那契数列转化为矩阵:
A={1 1}
  {1,0};

{f[n+1],f[n]}  
{f[n],f[n-1]} = A^n ;最后输出M.v[1][0]这就是构造斐波拉契数列的矩阵了。

这个题将式子化简之后我们可以得到
sum(f(g(n))) = A^(b)+A^(b+k)+...+A^(b+(n-1)*k) = A^b * (1+A^k+A^2k+...A^(n-1)k)
利用递归函数求解 A^k+A^2k+...A^(n-1)k 然后与 单位矩阵相加,最后还要判断 b是否为 0
很巧妙。
这里给出一个等比数列的求和公式.
LL cal(int p,int n){  ///这里是递归求解等比数列模板 1+p+p^2...+p^n
if(n==) return ;
if(n&){//(1+p+p^2+....+p^(n/2))*(1+p^(n/2+1));
return (+pow_mod(p,n/+))*cal(p,n/)%mod;
}
else { //(1+p+p^2+....+p^(n/2-1))*(1+p^(n/2+1))+p^(n/2);
return (pow_mod(p,n/)+(+pow_mod(p,n/+))*cal(p,n/-))%mod;
}
}
#include<stdio.h>
#include<iostream>
#include<string.h>
#include <stdlib.h>
#include<math.h>
#include<algorithm>
using namespace std;
typedef long long LL;
struct Martix{
LL v[][];
}res;
LL k,b,n,M; Martix mult(Martix a,Martix b){
Martix temp;
for(int i=;i<;i++){
for(int j=;j<;j++){
temp.v[i][j] = ;
for(int k=;k<;k++){
temp.v[i][j] = (temp.v[i][j]+a.v[i][k]*b.v[k][j])%M;
}
}
}
return temp;
} Martix add(Martix a,Martix b){
for(int i=;i<;i++){
for(int j=;j<;j++){
a.v[i][j]=(a.v[i][j]+b.v[i][j])%M;
}
}
return a;
}
Martix pow_mod(Martix a,LL k){
Martix ans;
ans.v[][]=ans.v[][] = ;
ans.v[][]= ans.v[][]=;
while(k){
if(k&) ans = mult(ans,a);
a=mult(a,a);
k>>=;
}
return ans;
} Martix cal(Martix p,LL k) ///用二分法求矩阵和,递归实现 计算 a^1+a^2.....+a^p
{
if(k==)
return p;
else if(k&)
return add(cal(p,k-),pow_mod(p,k));
else
return mult(cal(p,k>>),add(pow_mod(p,k>>),res));
} int main(){ Martix a,t;
a.v[][] = a.v[][] = a.v[][] = ; ///斐波拉契数列的特征值矩阵[1 1 1 0]
a.v[][] = ;
t.v[][] = t.v[][] = ; ///单位矩阵
t.v[][] = t.v[][] = ;
while(scanf("%lld%lld%lld%lld",&k,&b,&n,&M)!=EOF){
Martix M1 = pow_mod(a,k);
res = t;
res = add(t,cal(M1,n-));
if(b!=){
Martix M3 = pow_mod(a,b);
res = mult(res,M3);
}
printf("%d\n",res.v[][]%M);
}
return ;
}
 

最新文章

  1. 转:在Android中使用AlarmManager
  2. redis hash数据类型
  3. 【codevs1043】 方格取数
  4. php二维数组的取值与转换
  5. XunSearch(讯搜)的使用教程步骤
  6. 如何用OCR图文识别软件在文档里复制内容
  7. 14.8.9 Clustered and Secondary Indexes
  8. linux常用编辑器
  9. TIMESTAMP和DATETIME的区别
  10. ZS and The Birthday Paradox
  11. Oracle Database Transaction Isolation Levels 事务隔离级别
  12. 日志学习系列(三)——NLog基础知识
  13. .NET使用gRPC
  14. 关于使用easyui 中提示dialog is not a function的问题
  15. 【cf849D】Rooter&#39;s Song(思维)
  16. Django2.0引入css、js、img文件
  17. ImportError: No module named &#39;requests.packages.urllib3&#39;
  18. Codeforces E - Connected Components?
  19. Django is not importable in this environment
  20. SpringBoot集成JWT实现token验证

热门文章

  1. 转 Keras 保存与加载网络模型
  2. ubuntu16.04安装 java JDK8
  3. linux系统防火墙关闭
  4. Nordic Collegiate Programming Contest 2015​ G. Goblin Garden Guards
  5. hdu 6318
  6. oracle 控制文件的重建
  7. VirtualBox 安装XP虚拟机, 安装DB2
  8. [automator篇][9] 列表,找孩子
  9. Collection类及常用API
  10. poj1985&amp;&amp;第四次CCF软件认证第4题 求树的直径