CF755G PolandBall and Many Other Balls
Problem
有一排\(n(n\leq 10^9)\)个球,定义一个组可以只包含一个球或者包含两个相邻的球。现在一个球只能分到一个组中,求从这些球中取出\(k(k<2^{15})\)组的方案数。
Sol1(较优)
设\(f_{i,j}\)表示前\(i\)个数选了\(j\)组的方案数。有:
构造生成函数
由递推式,得
边界\(F_0(x)=1,F_1(x)=1+x\)
对于形如\(f_i=af_{i-1}+bf_{i-2}\)的数列,可以得到其通项公式为
其中\(x_1,x_2\)为方程\(x^2=ax+b\)的两根,\(A,B\)通过待定系数法求得。
暴力求解递推式,得到
其中\(t_1,t_2\)为方程\(t^2=(1+x)t+x\)的两根,这里\(t_1\)是正根,为\(\dfrac{1+x+\sqrt{x^2+6x+1}}2\)
注意到\(t_2^{n+1}\equiv 0\pmod{x^{n+1}}\),故最终答案
复杂度\(\mathcal O(k\log k)\)
Sol2(较劣)
\(n\)的范围很大,考虑对\(n\)下手。
首先,考虑合并两段序列时答案。设左边一段长度为\(a\),右边一段长度为\(b\),假设没有组跨过两段,则选取\(k\)组的方案数为
如果跨过中间,方案数为
总方案数为
还是用上文的生成函数,得到
代入特定的值
发现维护\(\{F_{n-2}(x),F_{n-1}(x),F_n(x)\}\)可以得到\(\{F_{2n-2}(x),F_{2n-1}(x),F_{2n}(x)\}\)
最后将\(k\)二进制分解,运用倍增以及上面的公式得到答案,复杂度\(\mathcal O(k\log k\log n)\),多出了\(\log n\)的复杂度。当然,直接对Sol1的递推式使用矩阵加速同样可以做到这个复杂度,其与Sol2无本质区别。