题面
解析
设$g_i$表示$sum_j a_j = i$的权值和,$g_0=0$,$f_i$表示斐波那契数列第$i$项,$g_i = sum_{j=1}^i g_{j}* f_{i-j}+f_i$
写成生成函数:设$G(x)=sum_{i=0}^{infty}g_i x^i$,$F(x)=sum_{i=0}^{infty}f_i x^i$,那么有:$$G=G*F+F\ G=frac{F}{1-F}$$
因为$f_i=f_{i-1}+f_{i-2}$,$f_0=0$,$f_1=1$,所以有:$$F=xF+x^2F+x\F=frac{x}{1-x-x^2}$$
代入$G$的表达式:$$G=frac{x}{1-2x-x^2}\ G=2xG+x^2G+x$$
即:$g_0=0$,$g_1=1$,$g_i=2g_{i-1}+g_{i-2}$
欧拉定理+矩阵快速幂
$O(log mod)$
代码:
#include<cstdio> #include<iostream> #include<algorithm> #include<cstring> using namespace std; const int maxn = 10005, mod = 1000000007; int add(int x, int y) { return x + y < mod? x + y: x + y - mod; } int n; char s[maxn]; struct matrix{ int a[2][2]; }dw0, dw1; matrix operator * (matrix x, matrix y) { matrix ret = dw0; for(int i = 0; i < 2; ++i) for(int j = 0; j < 2; ++j) for(int k = 0; k < 2; ++k) ret.a[i][j] = add(ret.a[i][j], 1LL * x.a[i][k] * y.a[k][j] % mod); return ret; } matrix mat_qpow(matrix x, int y) { matrix ret = dw1; while(y) { if(y&1) ret = ret * x; x = x * x; y >>= 1; } return ret; } int main() { scanf("%s", s + 1); int m = strlen(s + 1); for(int i = 1; i <= m; ++i) n = (10LL * n + s[i] - '0') % (mod - 1); dw1.a[0][0] = dw1.a[1][1] = 1; matrix A = dw0, ans = dw0; ans.a[0][1] = A.a[0][1] = A.a[1][0] = 1; A.a[1][1] = 2; ans = ans * mat_qpow(A, n); printf("%d", ans.a[0][0]); return 0; }