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 a 0,1 = 233,a 0,2 = 2333,a 0,3 = 23333...) Besides, in 233 matrix, we got a i,j = a i-1,j +a i,j-1( i,j ≠ 0). Now you have known a 1,0,a2,0,...,a n,0, could you tell me a n,m in the 233 matrix?
InputThere 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, a 1,0,a 2,0,...,a n,0(0 ≤ a i,0 < 2 31).OutputFor each case, output a n,m mod 10000007.Sample Input
1 1 1 2 2 0 0 3 7 23 47 16
Sample Output
234 2799 72937
#include<iostream> #include<cstdio> #include<cmath> #include<cstring> #include<sstream> #include<algorithm> #include<queue> #include<deque> #include<iomanip> #include<vector> #include<cmath> #include<map> #include<stack> #include<set> #include<fstream> #include<memory> #include<list> #include<string> using namespace std; typedef long long LL; typedef unsigned long long ULL; #define MAXN 18 #define N 33 #define MOD 10000007 #define INF 1000000009 const double eps = 1e-9; const double PI = acos(-1.0); /* 组合数学 找规律 递归显然不行,列数太多 只需考虑每个点被加上的次数 a(i,0) = a(i,1) 到 a(n,m) 路径条数(向左和向下两个方向) C(n+m-i-1,n) 发现列数太多没办法打表 再换一种方法 矩阵快速幂 从第一列向后考虑 找出他们的转移矩阵(这里很巧妙的加了一条边 凑2333后面的3)十分巧妙!~ */ LL a[MAXN], n, m; struct mat { LL data[MAXN][MAXN]; mat() { memset(data, 0, sizeof(data)); } mat operator*(const mat& rhs) { mat ret; for (int i = 1; i <= n + 2; i++) { for (int j = 1; j <= n + 2; j++) { for (int k = 1; k <= n + 2; k++) ret.data[i][j] = (ret.data[i][j] + data[i][k] * rhs.data[k][j]) % MOD; } } return ret; } }; mat fpow(mat a, LL b) { if (b <= 0) return a; mat tmp = a, ret; for (int i = 1; i <= n + 2; i++) ret.data[i][i] = 1; while (b!= 0) { if (b & 1) ret = tmp*ret; tmp = tmp*tmp; b = b / 2; } return ret; } int main() { while (cin >> n >> m) { a[1] = 23; for (int i = 2; i <= n + 1; i++) cin >> a[i]; a[n + 2] = 3; mat ans; for (int i = 1; i <= n + 1; i++) { ans.data[i][1] = 10; ans.data[i][n + 2] = 1; for (int j = 2; j <= i; j++) ans.data[i][j] = 1; } ans.data[n + 2][n + 2] = 1; ans = fpow(ans, m); LL result = 0; for (int i = 1; i <= n + 2; i++) result = (result + a[i] * ans.data[n + 1][i]) % MOD; cout << result << endl; } return 0; }