您的位置:首页 > 理论基础 > 计算机网络

HDU 5015 矩阵优化 (2014西安网络赛)

2014-09-15 23:47 337 查看
把所求的矩阵的第一行左移,由题意的运算规律可以退出一个 递推矩阵A,使得B[i]*(A)=B[i+1];

其中 B[0]如下:

B[0]=10;

B[1]=a1;

B[2]=a2;.....

.

B[n+1]=3;

矩阵加多前后两行 为了构造233.。。


//构造逆推矩阵,有矩阵快速幂优化m;

#include <cstdio>
#include <cstring>
#define mod 10000007
using namespace std;

typedef __int64 LL;
struct Mart
{
LL a[15][15];
Mart() {memset(a,0,sizeof(a));}
}A;

int n;
//构造A矩阵
void inti()
{
A.a[0][0]=10;
for(int i=1;i<=n;i++)
A.a[0][i]=0;
A.a[0][n+1]=1;

for(int i=1;i<=n;i++)
{
for(int j=0;j<=i;j++)
{
if(j<=i)
A.a[i][j]=1;
else
A.a[i][j]=0;
}
}

for(int i=0;i<=n;i++)
A.a[n+1][i]=0;
A.a[n+1][n+1]=1;
}

// 矩阵快速幂,模板
Mart multi(Mart m1,Mart m2)
{
Mart m;
for(int i=0;i<=n+1;i++)
for(int j=0;j<=n+1;j++)
for(int k=0;k<=n+1;k++)
m.a[i][j]=(m.a[i][j]+m1.a[i][k]*m2.a[k][j])%mod;
return m;
}

Mart getpow(Mart a,LL k)
{
Mart b;
for(int i=0;i<=n+1;i++)
b.a[i][i]=1;
while(k)
{
if(k&1) b=multi(b,a);
a=multi(a,a);
k>>=1;
}
return b;
}

int main()
{
LL m;
LL B[15];
B[0]=233;
while(~scanf("%d%I64d",&n,&m))
{
inti();
for(int i=1;i<=n;i++)
scanf("%I64d",&B[i]);
B[n+1]=3;
Mart C=getpow(A,m);

LL ans=0;
for(int i=0;i<=n+1;i++)
ans=(ans+C.a
[i]*B[i])%mod;

printf("%I64d\n",ans);
}
return 0;
}




内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: