poj 1141Brackets Sequence

来源:互联网 发布:大数据o2o概念股龙头 编辑:程序博客网 时间:2024/05/29 17:46
Brackets Sequence
Time Limit: 1000MS Memory Limit: 65536KTotal Submissions: 31629 Accepted: 9114 Special Judge

Description

Let us define a regular brackets sequence in the following way: 

1. Empty sequence is a regular sequence. 
2. If S is a regular sequence, then (S) and [S] are both regular sequences. 
3. If A and B are regular sequences, then AB is a regular sequence. 

For example, all of the following sequences of characters are regular brackets sequences: 

(), [], (()), ([]), ()[], ()[()] 

And all of the following character sequences are not: 

(, [, ), )(, ([)], ([(] 

Some sequence of characters '(', ')', '[', and ']' is given. You are to find the shortest possible regular brackets sequence, that contains the given character sequence as a subsequence. Here, a string a1 a2 ... an is called a subsequence of the string b1 b2 ... bm, if there exist such indices 1 = i1 < i2 < ... < in = m, that aj = bij for all 1 = j = n.

Input

The input file contains at most 100 brackets (characters '(', ')', '[' and ']') that are situated on a single line without any other characters among them.

Output

Write to the output file a single line that contains some regular brackets sequence that has the minimal possible length and contains the given sequence as a subsequence.

Sample Input

([(]

Sample Output

()[()]

题意:输出完整括号匹配后的字符串


题解:首先将dp[i][j]定义为,从i到j需要最少添加几个字符,vist[i][j]为i地址到j地址中,哪个地址分割,使得两边全部匹配,vist[i][j]为-1时,表示i,j两个位置完整匹配。

然后就是深搜输出字符,如果出现匹配,打印匹配字符,并向他们之间的区间继续深搜,,没出现的话,就在起点到中点的匹配分割点(vist)里面继续搜索。


#include <cstdio>#include <cstring>#include <algorithm>#include <iostream>#include <stack>#include <set>#include <queue>#define MAX(a,b) (a) > (b)? (a):(b)#define MIN(a,b) (a) < (b)? (a):(b)#define mem(a) memset(a,0,sizeof(a))#define INF 0x3f3f3f3f#define MAXN 20005using namespace std;#define N 300int dp[N][N];char str[N];int vist[N][N];int match(int i,int j){    if(str[i]=='('&&str[j]==')')        return 1;    if(str[i]=='['&&str[j]==']')        return 1;    return 0;}void dfs(int s,int n){    if(s>n)    {        return ;    }    if(s==n)    {        if(str[s]=='('||str[n]==')')            printf("()");        else            printf("[]");    }    else if(vist[s][n]==-1)    {        printf("%c",str[s]);        dfs(s+1,n-1);        printf("%c",str[n]);    }    else    {        dfs(s,vist[s][n]);        dfs(vist[s][n]+1,n);    }}int main(){    while(gets(str)!=NULL)///用scanf会WA(空格)    {        memset(dp,0,sizeof(dp));        int len=strlen(str);        for(int i=0; i<len; i++)        {            dp[i][i]=1;        }        int t;        for(int j=1; j<len; j++)        {            for(int i=0; i+j<len; i++)            {                int x=i+j;                dp[i][x]=INF;                if(match(i,x))                {                    dp[i][x]=dp[i+1][x-1];                    vist[i][x]=-1;                    printf("vist位置:%d %d-->%d\n\n",i,j,vist[i][j]);                    printf("匹配位置:%d %d\n\n",i,j);                }                for(int k=i; k<x; k++)                {                    t=dp[i][k]+dp[k+1][x];                    if(dp[i][x]>t)                    {                        dp[i][x]=t;                        printf("dp[%d][%d]= ",i,j);                        cout<<dp[i][j]<<endl;                        vist[i][x]=k;                        printf("vist位置 %d %d--->%d\n\n",i,j,vist[i][j]);                    }                }            }        }        dfs(0,len-1);        cout<<endl;    }    return 0;}


0 0
原创粉丝点击