poj3233

题意:给出矩阵A,求S = A + A2 + A3 + … + Ak

分析:把问题转化以加速,令

B = A  I

      0  I

则B^(k + 1) = A^(k + 1)      I + A + A2 + A3 + … + Ak

                            0                          I

用二分法求B^(k + 1)

View Code
#include <cstdio>
#include
<iostream>
#include
<cstdlib>
#include
<cstring>
usingnamespace std;

#define maxn 61

struct Matrix
{
int ma[maxn][maxn];
} b, ans;

int n, k, m;

void init()
{
memset(b.ma,
0, sizeof(b.ma));
memset(ans.ma,
0, sizeof(ans.ma));
scanf(
"%d%d%d", &n, &k, &m);
for (int i =0; i < n; i++)
for (int j =0; j < n; j++)
{
scanf(
"%d", &b.ma[i][j]);
b.ma[i][j]
%= m;
ans.ma[i][j]
= b.ma[i][j];
}
for (int i =0; i < n; i++)
{
b.ma[i][n
+ i] =1;
b.ma[n
+ i][n + i] =1;
ans.ma[i][n
+ i] =1;
ans.ma[n
+ i][n + i] =1;
}
}

void mul(Matrix &a, Matrix &b)
{
Matrix x;

for (int i =0; i < n *2; i++)
for (int j =0; j < n *2; j++)
x.ma[i][j]
= a.ma[i][j];
for (int i =0; i < n *2; i++)
for (int j =0; j < n *2; j++)
{
int sum =0;
for (int k =0; k < n *2; k++)
sum
+= x.ma[i][k] * b.ma[k][j];
a.ma[i][j]
= sum % m;
}
}

void sqr(Matrix &a)
{
Matrix x;

for (int i =0; i < n *2; i++)
for (int j =0; j < n *2; j++)
x.ma[i][j]
= a.ma[i][j];
mul(a, x);
}

void work(Matrix &a, int num)
{
if (num ==1)
return;
work(a, num
/2);
sqr(a);
if (num %2==1)
{
mul(a, b);
}
}

int main()
{
freopen(
"D:\\t.txt", "r", stdin);
init();
work(ans, k
+1);
for (int i =0; i < n; i++)
{
if (ans.ma[i][n + i] ==0)
ans.ma[i][n
+ i] = m;
ans.ma[i][n
+ i] -=1;
}
for (int i =0; i < n; i++)
{
printf(
"%d", ans.ma[i][n]);
for (int j =1; j < n; j++)
printf(
" %d", ans.ma[i][j + n]);
printf(
"\n");
}
return0;
}
posted @ 2011-02-21 21:34  金海峰  阅读(1160)  评论(0编辑  收藏  举报