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

歡迎訪問(wèn) 生活随笔!

生活随笔

當(dāng)前位置: 首頁(yè) > 编程资源 > 编程问答 >内容正文

编程问答

codeforces F.Fibonacci String Subsequences

發(fā)布時(shí)間:2023/12/3 编程问答 34 豆豆
生活随笔 收集整理的這篇文章主要介紹了 codeforces F.Fibonacci String Subsequences 小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

題意

定義F(x)為F(x-1)與F(x-2)的連接(其中F(0) = ‘0’,F(1) = ‘1’)。
給出一個(gè)長(zhǎng)度不超過(guò)100的字符串s,詢問(wèn)s在F(x)的所有子序列中出現(xiàn)了多少次。


題解

數(shù)量很大的計(jì)數(shù)問(wèn)題,我們首先想到的解決方案就是dp。
我們考慮F(x) = F(x-1) + F(x-2)
是由兩部分構(gòu)成的,我們可以分治來(lái)計(jì)算。
s[1,n]在F(x)中出現(xiàn)的次數(shù)由幾部分構(gòu)成:

  • s[1,n]s[1,n]F(x?1)F(x?1)中出現(xiàn)的次數(shù)乘以2len(F(x?2))2len(F(x?2))
  • s[1,n]s[1,n]F(x?2)F(x?2)中出現(xiàn)的次數(shù)乘以2len(F(x?1))2len(F(x?1))
  • s[1,k]s[1,k]F(x?1)F(x?1)中出現(xiàn)的次數(shù)*s[k+1,n]s[k+1,n]F(x?2)F(x?2)中出現(xiàn)的次數(shù)

我們定義狀態(tài)dp[i][l][r]dp[i][l][r]表示s[l,r]s[l,r]F(i)F(i)的所有子序列中出現(xiàn)的次數(shù)。
那么

dp[i][l][r]+=dp[i?1][l][r]?2len(F(i?2));當(dāng)r==n時(shí)dp[i][l][r]+=dp[i?1][l][r]?2len(F(i?2));當(dāng)r==n時(shí)候

解釋:當(dāng)r==n的時(shí)候,由于s[l,r]已經(jīng)在F(i-1)中結(jié)尾了,所以F(i-2)中可以隨便選取組成新的字串。

dp[i][l][r]+=dp[i?1][l][r]?1;當(dāng)r!=n時(shí)dp[i][l][r]+=dp[i?1][l][r]?1;當(dāng)r!=n時(shí)候

解釋:當(dāng)r!=n的時(shí)候,由于s[l,r]沒(méi)有在F(i-1)中結(jié)尾,此時(shí)如果取F(i-2)中字符的話,會(huì)給后面造成影響,即拼接出的包含s不是連續(xù)的。

dp[i][l][r]+=dp[i?2][l][r]?2len(F(i?1));當(dāng)l==1時(shí)dp[i][l][r]+=dp[i?2][l][r]?2len(F(i?1));當(dāng)l==1時(shí)候
dp[i][l][r]+=dp[i?2][l][r]?1;當(dāng)l!=1時(shí)dp[i][l][r]+=dp[i?2][l][r]?1;當(dāng)l!=1時(shí)候

然后就是s[l,r]s[l,r]分兩段s[l,k]s[l,k]F(i?1)F(i?1)里面和s[k+1,r]s[k+1,r]F(i?2)F(i?2)里面。
dp[i][l][r]+=dp[i][l][k]?dp[i][k+1][r],l<=k<rdp[i][l][r]+=dp[i][l][k]?dp[i][k+1][r],l<=k<r


實(shí)現(xiàn)代碼

#include <iostream> #include <cstdio> using namespace std; #define pr(x) cout<<#x<<':'<<x<<endl typedef long long ll; const int maxn = 107; const ll mod = 1e9+7; ll dp[maxn][maxn][maxn]; char s[maxn]; int n,m; ll modpow2[maxn]; int main(){scanf("%d%d",&m,&n);scanf(" %s",s);modpow2[0] = modpow2[1] = 2;for(int i = 2;i <= n;++i)modpow2[i] = modpow2[i-1]*modpow2[i-2]%mod;for(int i = 0;i < m;++i){dp[s[i]-'0'][i+1][i+1] = 1;}for(int i = 2;i <= n;++i){for(int l = 1;l <= m;++l){for(int r = l;r <= m;++r){dp[i][l][r] += dp[i-1][l][r]*(r == m?modpow2[i-2]:1)%mod;dp[i][l][r] += dp[i-2][l][r]*(l == 1?modpow2[i-1]:1)%mod;for(int k = l;k < r;++k){dp[i][l][r] += dp[i-1][l][k]*dp[i-2][k+1][r]%mod;}dp[i][l][r] %= mod;}}}cout<<dp[n][1][m]<<endl;return 0; }

總結(jié)

以上是生活随笔為你收集整理的codeforces F.Fibonacci String Subsequences的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。

如果覺(jué)得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。