您的位置:首页 > 产品设计 > UI/UE

URAL 1183

2013-08-23 11:21 197 查看
题目大意:给出一个长度为S的括号序列,求一个以此序列为子序列的最小合法序列。合法即:每种括号的每一个括号都有其相应的匹配。

Time Limit:1000MS Memory
Limit:65536KB 64bit IO Format:%I64d
& %I64u


数据规模:1<=S<=100。
理论基础:无。
题目分析:
将一个括号序列合法化无非有以下几种情况:
1.最左边括号与最右边括号匹配。合法化中间括号序列即可。
2.最左边序列与最右边括号不匹配。
1>.最左边括号为左括号,在最右边加右括号。合法化其余括号序列。
2>.最左边括号为右括号,在最左边加左括号。合法化其余括号序列。
3>.最右边括号为右括号,在最左边加左括号。合法化其余括号序列。
4>.最右边括号为左括号,在最右边加右括号。合法化其余括号序列。

答案为:合法化最左边至第j个位置的序列与j+1至最右边的序列,然后相加(最左边<=j<=最右边)得到序列中的长度最小的序列。

通过记忆化搜索即可实现。

代码如下:

#include<iostream>
#include<cstring>
#include<string>
#include<cstdlib>
#include<cstdio>
#include<cmath>
#include<algorithm>
#include<queue>
#include<ctime>
#include<vector>
using namespace std;
typedef double db;
#define DBG 1
#define maa (1<<31)
#define mii ((1<<31)-1)
#define ast(b) if(DBG && !(b)) { printf("%d!!|\n", __LINE__); while(1) getchar(); }  //调试
#define dout DBG && cout << __LINE__ << ">>| "
#define pr(x) #x"=" << (x) << " | "
#define mk(x) DBG && cout << __LINE__ << "**| "#x << endl
#define pra(arr, a, b)  if(DBG) {\
dout<<#arr"[] |" <<endl; \
for(int i=a,i_b=b;i<=i_b;i++) cout<<"["<<i<<"]="<<arr[i]<<" |"<<((i-(a)+1)%8?" ":"\n"); \
if((b-a+1)%8) puts("");\
}
template<class T> inline bool updateMin(T& a, T b) { return a>b? a=b, true: false; }
template<class T> inline bool updateMax(T& a, T b) { return a<b? a=b, true: false; }
typedef long long LL;
typedef long unsigned int LU;
typedef long long unsigned int LLU;
#define N 120
string dp[N+1][N+1],ch;
string solve(int l,int r)
{
if(l>r) return string();
if(dp[l][r].size())return dp[l][r];
string res;
if(l==r)
{
if(ch[l]=='('||ch[l]==')')res="()";
else res="[]";
}
else
{
if(ch[l]=='('&&ch[r]==')'||ch[l]=='['&&ch[r]==']')
{
res.push_back(ch[l]);
res+=solve(l+1,r-1);
res.push_back(ch[r]);
}
if(ch[l]=='('||ch[l]=='[')
{
string tr;
tr.push_back(ch[l]);
tr+=solve(l+1,r);
if(ch[l]=='(')tr.push_back(')');
else tr.push_back(']');
if(!res.size()||res.size()>tr.size())res=tr;
}
else
{
string tr;
tr=solve(l,l);
tr+=solve(l+1,r);
if(!res.size()||res.size()>tr.size())res=tr;
}
if(ch[r]==')'||ch[r]==']')
{
string tr;
if(ch[r]==')')tr.push_back('(');
else tr.push_back('[');
tr+=solve(l,r-1);
tr.push_back(ch[r]);
if(res.size()>tr.size())res=tr;
}
else
{
string tr;
tr=solve(l,r-1);
tr+=solve(r,r);
if(res.size()>tr.size())res=tr;
}
}
for(int i=l;i<r;i++)
{
string s1=solve(l,i);
string s2=solve(i+1,r);
if(res.size()>s1.size()+s2.size())res=s1+s2;
}
return dp[l][r]=res;
}
int main()
{
while(cin>>ch)
{
cout<<solve(0,ch.size()-1)<<endl;
}
return 0;
}


没有其中了,题目分析中已经说的很详细。

by:Jsun_moon http://blog.csdn.net/jsun_moon
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息