poj 1141 Brackets Sequence(区间DP记录路径)

来源:互联网 发布:大数据应用 央视新闻 编辑:程序博客网 时间:2024/06/16 08:00

题目链接:

http://poj.org/problem?id=1141

题目大意:

给一个不完全匹配的括号序列,问最少需要增加多少个括号能够使括号序列完全匹配,输出完全匹配以后的序列。

思路:

区间DP。我们设dp[i][j]代表i~j区间里面使得括号完全匹配最少需要增加的括号数。

那么如果s[i]和s[j]是匹配的,就有dp[i][j]=dp[i+1][j-1]。

然后就在i~j之间枚举k,同时更新dp[i][j]=min(dp[i][j],dp[i][k]+dp[k+1][j])。

这样我们就能够知道最少需要增加的括号数了。接下来我们就要考虑记录路径的问题了。

我们可以设一个p[i][j],初始化为-1。如果p[i][j]=k,就表示在区间i~j里面,在k这个位置有切入点需要添加新的括号。

所以我们可以采用递归的方式,来打印出路径。

代码:

#include<stdio.h>#include<string.h>char s[105],c[105];int p[105][105];void print(int i,int j){    if(i>j)return;     if(i==j){        if(s[i]=='('||s[i]==')')printf("()");        else printf("[]");        return;     }     if(i<j)     {         if(p[i][j]==-1){            if(s[i]=='(')            {                printf("(");                print(i+1,j-1);                printf(")");            }            else if(s[i]=='['){                printf("[");                print(i+1,j-1);                printf("]");            }         }         else         {             print(i,p[i][j]);         print(p[i][j]+1,j);         }     }}int main(){     int  dp[105][105],i,j,k,l;     while(gets(c))     {         l=strlen(c);         for(i=0;i<l;i++)            s[i+1]=c[i];         memset(dp,0,sizeof(dp));         memset(p,-1,sizeof(p));        for(i=1;i<=l;i++)        dp[i][i]=1;         for(k=2;k<=l;k++)         {             for(i=1;i<=l-k+1;i++)             {                 int zhong=i+k-1;                 if(s[i]=='('&&s[zhong]==')'||s[i]=='['&&s[zhong]==']')                    {dp[i][zhong]=dp[i+1][zhong-1];                    p[i][zhong]=-1;}                 else dp[i][zhong]=99999999;                 for(j=i;j<zhong;j++)                 {                     if(dp[i][zhong]>dp[i][j]+dp[j+1][zhong])                     {                         dp[i][zhong]=dp[i][j]+dp[j+1][zhong];                         p[i][zhong]=j;                     }                 }             }         }        // printf("%d\n",l);         print(1,l);         printf("\n");     }     return 0;}


0 0