【题解】CF1015F - Bracket Substring

思维不太难,但是这道题的模型和普通的还是有点不太一样。

提供一个字符串转移的新姿势。

d p [ i ] [ j ] [ k ] dp[i][j][k] dp[i][j][k] 表示前 i i i 个字符,有 j j j 个未匹配的左括号,且包含序列 s s s 的前 k k k 个元素的方案数。

需要写一个 KMP 来优化转移。然后就做完了 (雾

#include<bits/stdc++.h> #define ll long long #define inf 0x3f3f3f3f #define fi first #define se second #define pii pair<int,int> using namespace std; const int Maxn=405; const int mod=1e9+7; int n,m,f[Maxn],dp[2][Maxn][Maxn],g[Maxn][2]; char s[Maxn]; void Mod(int &x,int y) { x+=y; if(x>=mod) x-=mod; } signed main() { // freopen("data.in","r",stdin); scanf("%d%s",&n,s+1); m=strlen(s+1); f[1]=0; for(int i=2,j=0;i<=m;i++) { while(j&&s[j+1]!=s[i]) j=f[j]; if(s[j+1]==s[i]) j++; f[i]=j; // printf("f[%d]=%d\n",i,f[i]); } for(int i=1;i<=m;i++) { int j=f[i]; while(j&&s[j+1]!='(') j=f[j]; if(s[j+1]=='(') j++; g[i][0]=j; j=f[i]; while(j&&s[j+1]!=')') j=f[j]; if(s[j+1]==')') j++; g[i][1]=j; // printf("g[%d][0]=%d\ng[%d][1]=%d\n",i,g[i][0],i,g[i][1]); } dp[0][0][1]=1; for(int le=1;le<=n;le++) { for(int i=0;i<=1;i++) { memset(dp[i^1],0,sizeof dp[i^1]); for(int j=0;j<=le<<1;j++) { for(int k=1;k<=m+1;k++) { if(dp[i][j][k]) { // printf("dp[%d][%d][%d]=%d\n",i,j,k,dp[i][j][k]); if(k>m) { Mod(dp[i^1][j+1][k],dp[i][j][k]); if(j) Mod(dp[i^1][j-1][k],dp[i][j][k]); } else { if(s[k]=='(') { Mod(dp[i^1][j+1][k+1],dp[i][j][k]); if(j) Mod(dp[i^1][j-1][g[k-1][1]+1],dp[i][j][k]); } else { if(j) Mod(dp[i^1][j-1][k+1],dp[i][j][k]); Mod(dp[i^1][j+1][g[k-1][0]+1],dp[i][j][k]); } } } } } } } printf("%d",dp[0][0][m+1]); }

__EOF__

本文作者仰望星空的蚂蚁
本文链接https://www.cnblogs.com/cqbzly/p/17530250.html
关于博主:评论和私信会在第一时间回复。或者直接私信我。
版权声明:本博客所有文章除特别声明外,均采用 BY-NC-SA 许可协议。转载请注明出处!
声援博主:如果您觉得文章对您有帮助,可以点击文章右下角推荐一下。您的鼓励是博主的最大动力!
posted @   仰望星空的蚂蚁  阅读(5)  评论(0编辑  收藏  举报  
相关博文:
阅读排行:
· 全程不用写代码,我用AI程序员写了一个飞机大战
· MongoDB 8.0这个新功能碉堡了,比商业数据库还牛
· 记一次.NET内存居高不下排查解决与启示
· 白话解读 Dapr 1.15:你的「微服务管家」又秀新绝活了
· DeepSeek 开源周回顾「GitHub 热点速览」
点击右上角即可分享
微信分享提示