日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 默认站点!

默认站点

當前位置: 首頁 >

bzoj#4161-Shlw loves matrixI【常系数线性齐次递推】

發布時間:2023/12/3 26 豆豆
默认站点 收集整理的這篇文章主要介紹了 bzoj#4161-Shlw loves matrixI【常系数线性齐次递推】 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

正題

題目鏈接:https://darkbzoj.tk/problem/4161


題目大意

給出序列aaa,和hhh0~k?10\sim k-10k?1項,滿足
hn=∑i=1naihn?ih_n=\sum_{i=1}^na_ih_{n-i}hn?=i=1n?ai?hn?i?
hnh_nhn?

1≤n≤109,1≤k≤20001\leq n\leq 10^9,1\leq k\leq 20001n109,1k2000


解題思路

顯然k≤2000k\leq 2000k2000我們就不能矩陣乘法了,然后就去研究了一下常系數線性齊次遞推,而且這題k2k^2k2能過所以不用O(nlog?n)O(n\log n)O(nlogn)的多項式取模。

首先對于一個k×kk\times kk×k的矩陣AAA的特征多項式f(x)f(x)f(x)的定義是
f(x)=∑i=0kdet(A?kλ)xif(x)=\sum_{i=0}^kdet(A-k\lambda)x^if(x)=i=0k?det(A?kλ)xi
而我們知道對于這種遞推式的特征多項式就是
f(x)=xk?∑i=0k?1aixif(x)=x^k-\sum_{i=0}^{k-1}a_ix^if(x)=xk?i=0k?1?ai?xi

然后有個Cayley-Hamilton定理就是說對于AAA的特征多項式f(x)f(x)f(x)滿足f(A)=0f(A)=0f(A)=0

如果按照這種特殊的特征多項式去理解的話挺好懂的,但是實際上的就不會證了。

那么我們如果要求一個轉移矩陣An=Anmodf(A)A^n=A^n\mod f(A)An=Anmodf(A),我們可以求出一個多項式r(x)=xnmodf(x)r(x)=x^n\mod f(x)r(x)=xnmodf(x),然后直接把AAA帶入這個多項式就好了。

這個東西要用到快速冪+多項式取模,O(k2)O(k^2)O(k2)的話實現起來很簡單,考慮一個xk+i(i≥0)modf(x)x^{k+i}(i\geq 0)\mod f(x)xk+i(i0)modf(x)會發生什么,因為f(x)[k]=1f(x)[k]=1f(x)[k]=1所以?xk+if(x)?=xi\lfloor \frac{x^{k+i}}{f(x)}\rfloor=x^i?f(x)xk+i??=xi相當于把xi(f(x)?xk)x^i(f(x)-x^k)xi(f(x)?xk)再丟回去就好了。

然后我們得到了一個多項式r(x)r(x)r(x),考慮怎么計算答案,只需要計算An?kh?A^{n-k}\vec{h}An?kh的最后一項,所以我們實際上求的r(x)=xn?kmodf(x)r(x)=x^{n-k}\mod f(x)r(x)=xn?kmodf(x),記r(x)r(x)r(x)iii次系數為bib_ibi?,那么我們有
r(A)h?=∑i=0k?1biAih?r(A)\vec{h}=\sum_{i=0}^{k-1}b_iA^{i}\vec{h}r(A)h=i=0k?1?bi?Aih
所以我們算出hhhk~2k?1k\sim 2k-1k2k?1項然后就有
hn=∑i=0k?1r(x)[i]hk+ih_n=\sum_{i=0}^{k-1}r(x)[i]h_{k+i}hn?=i=0k?1?r(x)[i]hk+i?

時間復雜度:O(k2log?n)O(k^2\log n)O(k2logn)

值得一提的是如果轉移矩陣AAA不是一個遞推式的矩陣,我們也可以用拉格朗日插值插出它的特征多項式從而降低平均的復雜度。


code

#include<cstdio> #include<cstring> #include<algorithm> #define ll long long using namespace std; const ll N=4100,P=1e9+7; ll n,k,a[N],p[N],h[N],b[N],f[N],tmp[N]; void Mul(ll *a,ll *b,ll *c){memset(tmp,0,sizeof(tmp));for(ll i=0;i<k;i++)for(ll j=0;j<k;j++)(tmp[i+j]+=a[i]*b[j]%P)%=P;for(ll i=2*k-2;i>=k;i--)for(ll j=0;j<k;j++)(tmp[i+j-k]+=P-tmp[i]*p[j]%P)%=P;for(ll i=0;i<k;i++)c[i]=tmp[i];return; } signed main() {scanf("%lld%lld",&n,&k);for(ll i=1;i<=k;i++)scanf("%lld",&a[i]),a[i]=(a[i]+P)%P,p[k-i]=P-a[i];for(ll i=0;i<k;i++)scanf("%lld",&h[i]),h[i]=(h[i]+P)%P;for(ll i=k;i<(k<<1);i++)for(ll j=1;j<=k;j++)(h[i]+=h[i-j]*a[j]%P)%=P;if(n<(k<<1))return printf("%lld\n",h[n])&0;b[1]=p[k]=f[0]=1;ll B=n-k,ans=0;while(B){if(B&1)Mul(f,b,f);Mul(b,b,b);B>>=1;}for(ll i=0;i<k;i++)(ans+=f[i]*h[i+k]%P)%=P;printf("%lld\n",ans);return 0; }

總結

以上是默认站点為你收集整理的bzoj#4161-Shlw loves matrixI【常系数线性齐次递推】的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得默认站点網站內容還不錯,歡迎將默认站点推薦給好友。