hdu 4965 Fast Matrix Calculation
给出n*k的矩阵A k*n的矩阵B 4<=n<=1000 2<=k<=6 然后求A*B得到的新矩阵的n*n次幂 然后矩阵中所有元素%6
求出最后矩阵中所有元素的值
没想到 到了1000 结构体中开1010*1010的数组就不行了 然后始终保存 无法运行
这题其实思路很简单 就是矩阵快速幂
可以注意到 k的值很小 所以通过转化来将计算的矩阵转化为k*k的矩阵
(A*B)*(A*B)*(A*B)*(A*B)*(A*B)*……(A*B)括号内的值相乘n*n次
矩阵乘法的结合律可以将此转化为A*(B*A)*(B*A)*(B*A)*(B*A)*……*(B*A)*B 括号内的值相乘n*n-1次
这样就可以避免结构体内数组太大的问题了。。。代码很简单 主要要注意矩阵乘法循环内的条件
代码如下:
<span style="font-family:KaiTi_GB2312;font-size:18px;">#include <cstdio>
#include <iostream>
#include <cstring>
#include <cmath>
#include <algorithm>
#include <string.h>
#include <string>
#define eps 1e-8
#define op operator
#define mod 6
#define MAXN 100100
#define FOR(i,a,b) for(int i=a;i<=b;i++)
#define FOV(i,a,b) for(int i=a;i>=b;i--)
#define REP(i,a,b) for(int i=a;i<b;i++)
#define REV(i,a,b) for(int i=a-1;i>=b;i--)
#define MEM(a,x) memset(a,x,sizeof a)
#define ll __int64
using namespace std;
int n,k;
struct matrix
{
int a[10][10];
};
matrix ori,res;
void init()
{
memset(res.a,0,sizeof(res.a));
for(int i=0;i<k;i++)
res.a[i][i]=1;
}
matrix multiply(matrix x,matrix y)
{
// cout<<"aaa"<<endl;
matrix temp;
MEM(temp.a,0);
for(int i=0;i<k;i++)
{
for(int j=0;j<k;j++)
{
for(int m=0;m<k;m++)
{
temp.a[i][j]+=(x.a[i][m]*y.a[m][j]);
temp.a[i][j]%=mod;
}
}
}
return temp;
}
void calc(int num)
{
// cout<<"aaa"<<endl;
while(num)
{
if(num&1)
res=multiply(ori,res);
num>>=1;
ori=multiply(ori,ori);
}
// for(int i=0;i<k;i++)
// {
// for(int j=0;j<k;j++)
// cout<<res.a[i][j]<<"\t";
// cout<<endl;
// }
}
int p[1010][1010],q[1010][1010];
int ans1[1010][1010],ans2[1010][1010];
int main()
{
freopen("ceshi.txt","r",stdin);
while(scanf("%d%d",&n,&k)!=EOF)
{
if(n==0&&k==0) break;
init();
MEM(ori.a,0);
for(int i=0;i<n;i++)
for(int j=0;j<k;j++)
scanf("%d",&p[i][j]);
for(int i=0;i<k;i++)
for(int j=0;j<n;j++)
scanf("%d",&q[i][j]);
// cout<<"111111111111111111"<<endl;
for(int i=0;i<k;i++)
for(int j=0;j<k;j++)
{
for(int m=0;m<n;m++)
ori.a[i][j]+=q[i][m]*p[m][j];
// cout<<"1111"<<endl;
}
// for(int i=0;i<n;i++)
// {
// for(int j=0;j<n;j++)
// {
// cout<<ori.a[i][j]<<" ";
// }
// cout<<endl;
// }
// cout<<n*n<<endl;
calc(n*n-1);
MEM(ans1,0); MEM(ans2,0);
for(int i=0;i<n;i++)
for(int j=0;j<k;j++)
for(int m=0;m<k;m++)
{
ans1[i][j]+=p[i][m]*res.a[m][j];
ans1[i][j]%=6;
}
for(int i=0;i<n;i++)
for(int j=0;j<n;j++)
for(int m=0;m<k;m++)
{
ans2[i][j]+=ans1[i][m]*q[m][j];
ans2[i][j]%=6;
}
int sum=0;
for(int i=0;i<n;i++)
for(int j=0;j<n;j++)
{
sum+=(ans2[i][j]%mod);
}
printf("%d\n",sum);
}
return 0;
}
</span>
有时间了 也要写下用stl存储的方法!!!!!