Description
定义斐波那契数 (F_1=1,F_2=1,F_n=F_{n-1}+F_{n-2}),整数的 lqp 拆分是满足任意 (m>0),(a_1 ,a_2 ,a_3…a_m>0),且 (a_1+a_2+a_3+…+a_m=n) 的一个有序集合。定义这个拆分的权值 (F_{a_1}F_{a_2}…F_{a_m}),对于所有的拆分,权值之和 (sumprod_{i=1}^m F_{a_i}) 是多少?
Solution
推导 Fib 数列的生成函数
(A=1+x+2x^2+3x^3+5x^4+...)
于是有
(xA=x+x^2+2x^3+3x^4+5x^5)
(x^2A=x^2+x^3+2x^4+3x^5+5x^6)
做差得
[A=frac 1 {1-x-x^2}
]
本题中由于整体右移了一位,修正为
[A=frac x {1-x-x^2}
]
于是答案为
[G=sum_{i=0}^infty A^i=frac 1 {1-F}=frac {1-x-x^2}{1-2x-x^2}=1+frac {x}{1-2x-x^2}
]
考虑到 (1-2x-x^2=(1-(1+sqrt 2)x)(1-(1-sqrt 2)x)),
解得 (x_1=-sqrt 2 +1, x_2 = sqrt 2 +1)
于是,设 (g_n = c_1(-sqrt 2 +1)^n + c_2 (sqrt 2 +1)^n)
利用 (n=0,1) 定出
[c_1 = frac {sqrt 2 -1}{2sqrt 2} , quad c_2 = frac {sqrt 2 + 1}{2 sqrt 2}
]
于是暴力用二次剩余算出各项的值,然后快速幂即可,注意把 (n) 模上 (mod-1)
#include <bits/stdc++.h>
using namespace std;
#define int long long
const int mod = 1e9+7;
int qpow(int p,int q)
{
return (q&1?p:1)*(q?qpow(p*p%mod,q/2):1)%mod;
}
int inv(int p)
{
return qpow(p,mod-2);
}
namespace cipolla
{
inline int le(int x)
{
return qpow(x,(mod-1)/2);
}
int w;
struct comp
{
int x,y;
comp(int a=0,int b=0)
{
x=a;
y=b;
}
};
comp operator + (comp a,comp b)
{
return comp((a.x+b.x)%mod,(a.y+b.y)%mod);
}
comp operator - (comp a,comp b)
{
return comp((a.x-b.x+mod)%mod,(a.y-b.y+mod)%mod);
}
comp operator * (comp a,comp b)
{
return comp((a.x*b.x+a.y*b.y%mod*w)%mod,(a.x*b.y+a.y*b.x)%mod);
}
comp operator ^ (comp a,int b)
{
comp o(1,0);
for(; b; a=a*a,b>>=1) if(b&1) o=o*a;
return o;
}
int calc(int x)
{
x%=mod;
int a;
while(true)
{
a=rand();
w=(a*a-x+mod)%mod;
if(le(w)==mod-1) break;
}
comp s=comp(a,1)^((mod+1)/2);
return min(s.x,mod-s.x);
}
}
int n;
signed main()
{
ios::sync_with_stdio(false);
string s;
cin>>s;
for(int i=0;i<s.length();i++)
{
int t=s[i]-'0';
n=(n*10+t)%(mod-1);
}
int sq2=cipolla::calc(2),sp2=sq2;
int c1=(sq2-1)*inv(2*sp2%mod)%mod, c2=(sq2+1)*inv(2*sp2%mod)%mod;
int x1=(-sq2+1+mod)%mod, x2=(sq2+1)%mod;
cout<<(c1*qpow(x1,n-1)+c2*(qpow(x2,n-1)))%mod<<endl;
}