hdu 4628 动态规划
思路:首先就是状态压缩,然后判断哪些状态是回文串。最后就是动态方程:dp[i]=min(dp[i],dp[j]+1)。这个方程得前提条件是状态(j-i)为回文串。
#include<iostream> #include<cstdio> #include<cstring> #define inf 1<<30 using namespace std; int pl[1<<20],dp[1<<20],n,l; char str[20]; int ispl(int x) { char s[20]; int cnt=0,i; for(i=0;i<=l;i++) { if(x&(1<<i)) s[cnt++]=str[i]; } s[cnt]='\0'; int len=strlen(s); for(i=0;i<len;i++) { if(s[i]!=s[len-i-1]) return 0; } return 1; } void init() { memset(pl,0,sizeof(pl)); memset(dp,0,sizeof(dp)); } int main() { int t,i,j; scanf("%d",&t); while(t--) { init(); scanf("%s",&str); l=strlen(str); n=1<<l; n-=1; for(i=1;i<=n;i++) { if(ispl(i)) pl[i]=1; } dp[n]=0; for(i=n-1;i>=0;i--) { dp[i]=inf; for(j=i+1;j<=n;j=((j+1)|i)) { if(pl[j-i]) dp[i]=min(dp[i],dp[j]+1); } } printf("%d\n",dp[0]); } return 0; }