首页 > 代码库 > FZU 1683 纪念SlingShot(矩阵快速幂)
FZU 1683 纪念SlingShot(矩阵快速幂)
题目地址:FZU 1683
这题一开始用的二分矩阵,于是就一直TLE。后来找题解才发现,可以不用二分矩阵,因为这个题最终求的是一个值,所以可以把那个值加入到构造的矩阵中:
这样就不用二分矩阵了。而是可以直接求。但是这样还是会超时,那怎么办呢。由于本题的模数是固定的,所以矩阵的幂也是固定的。那么就可以对一些2^x幂预处理出来。
代码如下:
#include <iostream> #include <cstdio> #include <string> #include <cstring> #include <stdlib.h> #include <math.h> #include <ctype.h> #include <queue> #include <map> #include <set> #include <algorithm> using namespace std; const int mod =2009; struct matrix { int ma[5][5]; } init, res, mat[40]; matrix Mult(matrix x, matrix y) { matrix tmp; int i, j, k; for(i=0; i<4; i++) { for(j=0; j<4; j++) { tmp.ma[i][j]=0; for(k=0; k<4; k++) { tmp.ma[i][j]=(tmp.ma[i][j]+x.ma[i][k]*y.ma[k][j])%mod; } } } return tmp; } matrix Pow(matrix x, int k) { int i, j, cnt=0; //for(i=0; i<4; i++) for(j=0; j<4; j++) tmp.ma[i][j]=(i==j); while(k) { if(k&1) x=Mult(mat[cnt],x); k>>=1; cnt++; } return x; } void per() { int i; mat[0]=init; for(i=1; i<32; i++) { mat[i]=Mult(mat[i-1],mat[i-1]); } } int main() { int t, i, j, k, num=0; scanf("%d",&t); memset(init.ma,0,sizeof(init.ma)); init.ma[0][0]=init.ma[0][1]=init.ma[2][1]=init.ma[3][2]=1; init.ma[1][1]=3; init.ma[1][2]=2; init.ma[1][3]=7; per(); while(t--) { num++; scanf("%d",&k); printf("Case %d: ",num); if(k==0) puts("1"); else if(k==1) puts("4"); else { res=Pow(init,k-1); int ans=res.ma[0][0]*4+res.ma[0][1]*5+res.ma[0][2]*3+res.ma[0][3]; ans%=mod; printf("%d\n",ans); } } return 0; }
FZU 1683 纪念SlingShot(矩阵快速幂)
声明:以上内容来自用户投稿及互联网公开渠道收集整理发布,本网站不拥有所有权,未作人工编辑处理,也不承担相关法律责任,若内容有误或涉及侵权可进行投诉: 投诉/举报 工作人员会在5个工作日内联系你,一经查实,本站将立刻删除涉嫌侵权内容。