哈工大 3772 矩阵+线段树
http://acm.zju.edu.cn/onlinejudge/showProblem.do?problemCode=3772
ac 代码
1 #include<iostream> 2 #include<cstdio> 3 #include<cstring> 4 #define mod 1000000007 5 using namespace std; 6 7 struct node{long long mat[2][2];} a[100002]; 8 struct node2{int l,r; node matrix;} tree[440004]; //树的节点 9 10 node mul(node a,node b) // 两个矩阵 相乘 返回 node型 11 { 12 node c; 13 int i,j,k; 14 for(i=0;i<2;i++) 15 { 16 for(j=0;j<2;j++) 17 { 18 c.mat[i][j]=0; 19 for(k=0;k<2;k++) 20 { 21 c.mat[i][j]=(c.mat[i][j]+a.mat[i][k]*b.mat[k][j])%mod; 22 } 23 //c.mat[i][j]=c.mat[i][j]%mod; 24 } 25 } 26 return c; 27 } 28 29 node2 build(int l,int r,int k) // tree[k] a[l]*** a[r] 30 { 31 tree[k].l=l; 32 tree[k].r=r; 33 if(l==r) 34 { 35 tree[k].matrix.mat[0][0]=a[l].mat[0][0]; 36 tree[k].matrix.mat[0][1]=a[l].mat[0][1]; 37 tree[k].matrix.mat[1][0]=a[l].mat[1][0]; 38 tree[k].matrix.mat[1][1]=a[l].mat[1][1]; 39 return tree[k]; 40 } 41 int mid; 42 mid=(l+r)/2; 43 build(l,mid,k*2); 44 build(mid+1,r,k*2+1); 45 tree[k].matrix=mul(tree[k*2].matrix,tree[k*2+1].matrix); 46 } 47 48 node ans(int x,int y,int k) 49 { 50 if(tree[k].l>=x&&tree[k].r<=y) 51 return tree[k].matrix; 52 53 int mid; 54 mid=(tree[k].l+tree[k].r)/2; 55 if(y<=mid) 56 return ans(x,y,k*2); 57 else if(x>=mid+1) 58 return ans(x,y,k*2+1); 59 return mul(ans(x,mid,k*2),ans(mid+1,y,k*2+1)); 60 } 61 62 void qus(int l,int r)// 63 { 64 if(r==l||r-1==l) 65 { 66 printf("%lld\n",a[r].mat[1][0]); 67 return ; 68 } 69 node temp; 70 temp=ans(l+2,r,1); 71 long long final1; 72 73 final1=(a[l+1].mat[1][0]*temp.mat[0][0]+a[l].mat[1][0]*temp.mat[1][0])%mod; 74 printf("%lld\n",final1); 75 } 76 77 int main() 78 { 79 int t,n,m,l,r; 80 long long x; 81 scanf("%d",&t); 82 while(t--) 83 { 84 scanf("%d%d",&n,&m); 85 for(int i=1;i<=n;i++) 86 { 87 scanf("%lld",&x); 88 a[i].mat[0][0]=1; a[i].mat[0][1]=1; 89 a[i].mat[1][0]=x; a[i].mat[1][1]=0; 90 } 91 build(1,n,1); 92 while(m--) 93 { 94 scanf("%d%d",&l,&r); 95 qus(l,r); 96 } 97 } 98 return 0; 99 }