题解报告:poj 3233 Matrix Power Series

题目链接:http://poj.org/problem?id=3233

Description

Given a n × n matrix A and a positive integer k, find the sum S = A + A2 + A3 + … + Ak.

Input

The input contains exactly one test case. The first line of input contains three positive integers n (n ≤ 30), k (k ≤ 109) and m (m < 104). Then follow n lines each containing n nonnegative integers below 32,768, giving A’s elements in row-major order.

Output

Output the elements of S modulo m in the same way as A is given.

Sample Input

2 2 4
0 1
1 1

Sample Output

1 2
2 3
解题思路:等比矩阵求和,参考了一下别人的写法,链接:poj3233 又见矩阵,不过是等比吗?;不错,求前k项和用递归比较好理解。
AC代码:
 1 #include<iostream>
 2 #include<cstring>
 3 using namespace std;
 4 const int maxn=35;
 5 int n,k,mod;
 6 struct Matrix
 7 {
 8     int m[maxn][maxn];
 9 }init;
10 Matrix add(Matrix a,Matrix b){//两个矩阵相加
11     Matrix c;
12     for(int i=0;i<n;++i)
13         for(int j=0;j<n;++j)
14             c.m[i][j]=(a.m[i][j]+b.m[i][j])%mod;
15     return c;
16 }
17 Matrix mul(Matrix a,Matrix b)//两个矩阵相乘
18 {
19     Matrix c;
20     for(int i=0;i<n;i++){
21         for(int j=0;j<n;j++){
22             c.m[i][j]=0;
23             for(int k=0;k<n;k++)
24                 c.m[i][j]=(c.m[i][j]+a.m[i][k]*b.m[k][j]%mod)%mod;
25             c.m[i][j]%=mod;
26         }
27     }
28     return c;
29 }
30 Matrix POW(Matrix a,int x)//矩阵快速幂
31 {
32     Matrix b;
33     memset(b.m,0,sizeof(b.m));
34     for(int i=0;i<n;++i)b.m[i][i]=1;//单位矩阵
35     while(x){
36         if(x&1)b=mul(b,a);
37         a=mul(a,a);
38         x>>=1;
39     }
40     return b;
41 }
42 Matrix sum(Matrix s,int k){//求前k项和
43     if(k==1)return s;//递归出口,如果幂指数为1,返回当前矩阵
44     Matrix tmp;//用来保存答案
45     memset(tmp.m,0,sizeof(tmp.m));
46     for(int i=0;i<n;++i)tmp.m[i][i]=1;//单位矩阵
47     tmp=add(tmp,POW(s,k>>1));//计算1+A^(k/2)
48     tmp=mul(tmp,sum(s,k>>1));//计算(1+A^(k/2))*(A + A^2 + A^3 + … + A^(k/2))=(1+A^(k/2))*(Sk/2)
49     if(k&1)tmp=add(tmp,POW(s,k));//若k是奇数,则加上A^k
50     return tmp;//返回前k项的值
51 }
52 void print_rectangle(Matrix r){
53     for(int i=0;i<n;++i)
54         for(int j=0;j<n;++j)
55             cout<<r.m[i][j]<<((j==n-1)?"\n":" ");
56 }
57 int main()
58 {
59     while(cin>>n>>k>>mod){
60         for(int i=0;i<n;++i)
61             for(int j=0;j<n;++j)
62                 cin>>init.m[i][j];
63         init=sum(init,k);
64         print_rectangle(init);
65     }
66     return 0;
67 }

猜你喜欢

转载自www.cnblogs.com/acgoto/p/9082806.html