zoukankan      html  css  js  c++  java
  • HDU6799:Parentheses Matching——题解

    http://acm.hdu.edu.cn/showproblem.php?pid=6799

    给一个含有'(',')','*'的字符串,允许把‘*’变为‘(’或‘)’或‘’,求最小的括号匹配合法序列。

    签到题,当然我很傻没看条件WA了。

    想要构造最小长度的序列的话首先就是要减少'*'的使用,那么在原序列中就要尽可能的先匹配好一些括号。

    然后可以发现右括号都集中在左边,然后左括号都集中在右边,于是要构造最小的序列的话就对于右括号来说,尽可能的选靠左的‘*’变左括号,而对于左括号来说,尽可能的选靠右的‘*’变右括号即可。

    然后在刚才的过程中就可以判断串是否有解了,这个比较基础。

    #include<stack>
    #include<queue>
    #include<cstdio>
    #include<cstring>
    #include<iostream>
    #include<algorithm>
    #define fi first
    #define se second
    using namespace std;
    typedef long long ll;
    typedef pair<char,int>pii;
    const int N=1e5+5;
    inline int read(){
        int X=0,w=0;char ch=0;
        while(!isdigit(ch)){w|=ch=='-';ch=getchar();}
        while(isdigit(ch))X=(X<<3)+(X<<1)+(ch^48),ch=getchar();
        return w?-X:X;
    }
    stack<pii>q;
    char s[N];
    char t[N];
    int main(){
        int T=read();
        while(T--){
            scanf("%s",s+1);
            
            int n=strlen(s+1);
            for(int i=1;i<=n;i++){
                t[i]=s[i];
                if(s[i]=='(')q.push(pii(s[i],i));
                if(s[i]==')'){
                    if(!q.empty()){
                        t[q.top().se]=t[i]=0;
                        q.pop();
                    }
                }
            }
            while(!q.empty()){
                q.pop();
            }
            bool flag=1;
            int l=n+1,ls=0,rs=0;
            for(int i=1;i<=n;i++){
                if(t[i]=='*')ls++;
                if(t[i]==')'){
                    if(!ls){
                        flag=0;
                        break;
                    }
                    ls--;
                    rs++;
                }
                if(t[i]=='('){
                    l=i;
                    break;
                }
            }
            for(int i=1;i<=n;i++){
                if(t[i]=='*'&&rs){
                    rs--;
                    s[i]='(';
                }
            }
            ls=0;rs=0;
            for(int i=n;i>=l;i--){
                if(t[i]=='*')rs++;
                if(t[i]=='('){
                    if(!rs){
                        flag=0;
                        break;
                    }
                    rs--;
                    ls++;
                }
            }
            for(int i=n;i>=l;i--){
                if(t[i]=='*'&&ls){
                    ls--;
                    s[i]=')';
                }
            }
            if(!flag)puts("No solution!");
            else{
                for(int i=1;i<=n;i++){
                    if(s[i]=='('||s[i]==')'){
                        putchar(s[i]);
                    }
                }
                puts("");
            }
        }
        return 0;
    }

    +++++++++++++++++++++++++++++++++++++++++++

     +本文作者:luyouqi233。               +

     +欢迎访问我的博客:http://www.cnblogs.com/luyouqi233/+

    +++++++++++++++++++++++++++++++++++++++++++

  • 相关阅读:
    如何:通过对字符串应用 HTML 编码在 Web 应用程序中防止脚本侵入
    ref和out的区别?
    debug版本和release版本的区别?
    Ninject依赖注入——构造函数的注入
    WCF入门简单教程(图文) VS2010版
    WCF学习笔记(一)
    WinRt BottomAppBar
    windows 8.1 MessageDialog
    sqlServer学习2-sql脚本说明
    sqlServer学习1-sql脚本
  • 原文地址:https://www.cnblogs.com/luyouqi233/p/13392672.html
Copyright © 2011-2022 走看看