一开始把它当成暴力来做了,即,从终点开始,枚举其最长的回文串,一旦是最长的,马上就ans++,再计算另外的部分。。。结果WA了
事实证明就是一个简单DP,算出两个两个点组成的线段是否为回文,再用LCS的类似做法得到每个子结构的最优值。
#include <cstdio> #include <cstring> #define N 1010 char s[N]; int n,len,d[N][N],sum[N]; int min(int a,int b) { if (a<b) return a; return b; } int ok(int a,int b) { for (int i=a,j=b;i<j;i++,j--) { if (s[i]!=s[j]) return 0; } return 1; } int main() { scanf("%d",&n); for (int i=0;i<n;i++) { scanf("%s",s); len=strlen(s); int k,q,ans=0; for (int i=0;i<len;i++) { sum[i]=N; for (int j=0;j<=i;j++) { d[j][i]=ok(j,i); } } sum[0]=1; for (int i=1;i<len;i++) { for (int j=0;j<=i;j++) { //printf("%d %d %d ",j,i,d[j][i]); if (d[j][i]) { int tmp; if (j>0) { tmp=1+sum[j-1]; } else tmp=1; sum[i]=min(sum[i],tmp); } } } printf("%d ",sum[len-1]); } return 0; }