标签:maxx Palindromes int Number long Queries 区间 dp define
题意:给定一个字符串,求区间[l,r]内有多少回文子串。
解:回文杀我。区间dp++
首先这玩意不能像前缀和一样[l,r]=[1,r]-[1,l-1]。
那就直接设dp[i][j]为[i,j]中回文子串的数量。
考虑拿小的拼大的。如果两端不等,
dp[i][j]=dp[i+1][j]+dp[i][j-1]-dp[i+1][j-1];
如果相等在此基础上加一。有空补补容斥原理。
然后是遍历的顺序。区间dp从小区间到大区间,这题因为只有相邻两个之间可以谈转移,所以两重循环就够了。区间长度为2的时候特判一下,因为vis[i+1][j-1]会没有orz
代码:
#include<bits/stdc++.h> using namespace std; #define ll long long #define maxx 5005 #define eps 0.00000001 #define inf 0x3f3f3f3f #define mod 1000000007 //#define int long long char s[maxx]; int dp[maxx][maxx]={0}; int vis[maxx][maxx]={0}; signed main() { scanf("%s",s+1); int n=strlen(s+1); for(int i=1;i<=n;i++){ dp[i][i]=1; vis[i][i]=1; } for(int len=2;len<=n;len++){ for(int i=1;i<=n-len+1;i++){ int j=i+len-1; dp[i][j]=dp[i+1][j]+dp[i][j-1]-dp[i+1][j-1]; if((len!=2&&vis[i+1][j-1]&&s[i]==s[j])||(len==2&&s[i]==s[j])){ vis[i][j]=1; dp[i][j]++; } } } int q; scanf("%d",&q); while(q--){ int l,r; scanf("%d%d",&l,&r); printf("%d\n",dp[l][r]); } return 0; }View Code
标签:maxx,Palindromes,int,Number,long,Queries,区间,dp,define 来源: https://www.cnblogs.com/capterlliar/p/15737742.html
本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享; 2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关; 3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关; 4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除; 5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。