HDU 5015 233 Matrix

来源:互联网 发布:mac下制作u盘linux 编辑:程序博客网 时间:2024/06/07 09:51

233 Matrix

Time Limit: 10000/5000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Others)
Total Submission(s): 2504    Accepted Submission(s): 1454


Problem Description
In our daily life we often use 233 to express our feelings. Actually, we may say 2333, 23333, or 233333 ... in the same meaning. And here is the question: Suppose we have a matrix called 233 matrix. In the first line, it would be 233, 2333, 23333... (it means a0,1 = 233,a0,2 = 2333,a0,3 = 23333...) Besides, in 233 matrix, we got ai,j = ai-1,j +ai,j-1( i,j ≠ 0). Now you have known a1,0,a2,0,...,an,0, could you tell me an,m in the 233 matrix?
 

Input
There are multiple test cases. Please process till EOF.

For each case, the first line contains two postive integers n,m(n ≤ 10,m ≤ 109). The second line contains n integers, a1,0,a2,0,...,an,0(0 ≤ ai,0 < 231).
 

Output
For each case, output an,m mod 10000007.
 

Sample Input
1 112 20 03 723 47 16
 

Sample Output
234279972937
Hint
 

Source
2014 ACM/ICPC Asia Regional Xi'an Online

题意:给一个n * m的矩阵,a[0][0]=0,a[0][1]=233,a[0][2]=2333,a[n][0]自己输入,a[i][j]=a[i-1][j]+a[i][j-1],求a[n][m],mod上1e7+7,不是1e9+7
开始一直过不了样例,仔细一看mod错数了,解题思路也很简单,就是构造矩阵,然后快速幂

1   0   0  0  0  0  0   .......                           3
1  10  0  0  0  0  0   .......                           23
1  10  1  0  0  0  0   .......           X             a1
1  10  1  1  1  1  0   .......                           .....
1  10  1  1  1  1  1   .......                           an

矩阵的写法可能不太一样,很多人喜欢封装成一个类,我喜欢直接用数组,不过能对就好

#include<iostream>#include<cstdio>#include<algorithm>#include<cstring>#include<string>#include<stack>#include<queue>#include<deque>#include<set>#include<map>#include<cmath>#include<vector>using namespace std;typedef long long ll;typedef unsigned long long ull;typedef pair<int, int> PII;#define pi acos(-1.0)#define eps 1e-10#define pf printf#define sf scanf#define lson rt<<1,l,m#define rson rt<<1|1,m+1,r#define e tree[rt]#define _s second#define _f first#define all(x) (x).begin,(x).end#define mem(i,a) memset(i,a,sizeof i)#define for0(i,a) for(int (i)=0;(i)<(a);(i)++)#define for1(i,a) for(int (i)=1;(i)<=(a);(i)++)#define mi ((l+r)>>1)#define sqr(x) ((x)*(x))const int inf=0x3f3f3f3f;const int mod=1e7+7;ll p[20],ans[20][20],q[20],a[20][20];int m,n;void multi(ll a[][20],ll b[][20])//矩阵乘积{    ll tmp[20][20];    mem(tmp,0);    for1(i,19)        for1(j,19)            for1(k,19)                tmp[i][j]=(tmp[i][j]+a[i][k]*b[k][j])%mod;//乘积可能爆int    for1(i,19)        for1(j,19)            a[i][j]=tmp[i][j];}void init()//矩阵初始化{    mem(ans,0);    for1(i,19)        ans[i][i]=1;    mem(a,0);    for1(i,n+2)        for1(j,i)            a[i][j]=j==2?10:1;}int main(){    q[0]=0,p[1]=3,p[2]=23;//q保存m为0时的答案,p保存实际计算时的数组    while(~sf("%d%d",&n,&m))    {        init();//每次数组都要初始化一遍        for1(i,n)            sf("%I64d",&q[i]),p[2+i]=q[i];        if(!m)//m为0特判一下        {            pf("%I64d\n",q[n]%mod);            continue;        }        while(m)//快速幂        {            if(m&1)multi(ans,a);            multi(a,a);            m>>=1;        }        ll sum=0;//        for1(i,n+2)//            for1(j,n+2)//                pf(j==n+2?"%d\n":"%d ",ans[i][j]);        for1(i,n+2)            sum=(sum+ans[n+2][i]*p[i]%mod)%mod;        pf("%I64d\n",sum);    }    return 0;}