zoukankan      html  css  js  c++  java
  • hdu 6299 Balanced Sequence(贪心)题解

    题意:题意一开始不是很明白...就是他给你n个串,让你重新排列组合这n个串(每个串内部顺序不变),使得匹配的括号长度最大。注意,题目要求not necessary continuous,括号匹配不需要连续。

    思路:我们先把每个串里面能组合的全部抵消,比如)((()抵消完为)((。我们能知道,这样操作完只会有4种情况留下:))))),((((((((,)((((((,))))))))(。然后排序,排序的时候为了后面匹配能最大化利用所有括号,我们需要把左括号尽可能多的放在左边,右括号尽可能多的放在右边。

    我觉得还是这样理解排序吧:我们需要匹配最大的匹配串,那么我们要尽可能创造出(),最好全是(((((((((和))))))))这种直接放左右两端,但是事实上我们还有)(((((和))))))((这两种,这两种怎么排呢?我们可以这样想:对于左括号比右括号多的,我们把他们放在左边更赚,这样左括号能更多的和下面的右括号匹配。但是如果两个都是左括号比右括号多呢?那就看谁的右括号更少,少的放前面,这样浪费右括号的可能性更少。另一种同理。

    代码:

    #include<cstdio>
    #include<vector>
    #include<stack>
    #include<queue>
    #include<cstring>
    #include<string>
    #include<cmath>
    #include<cstdlib>
    #include<algorithm>
    #define ll long long
    const int maxn = 100000+5;
    const int maxm = 100000+5;
    const int MOD = 1e7;
    const int INF = 0x3f3f3f3f;
    using namespace std;
    struct node{
        int l,r;
    }p[maxn];
    bool cmp(node a,node b){
        if(a.l > a.r) return b.l > b.r? a.r < b.r : true;
        if(a.l <= a.r) return b.l <= b.r? a.l > b.l :  false;
    }
    char s[maxn];
    int main(){
        int n;
        int T;
        scanf("%d",&T);
        while(T--){
           scanf("%d",&n);
           int ans = 0;
           for(int i = 1;i <= n;i++){
                scanf("%s",s);
                int len = strlen(s);
                p[i].l = p[i].r = 0;
                for(int j = 0;j < len;j++){
                    if(s[j] == '(') p[i].l++;
                    else{
                        if(p[i].l > 0){
                            p[i].l--;
                            ans += 1;
                        }
                        else{
                            p[i].r++;
                        }
                    }
                }
           }
           int unused = 0;
           sort(p + 1,p + n + 1,cmp);
           for(int i = 1;i <= n;i++){
                if(p[i].r > unused) p[i].r = unused;
                ans += p[i].r;
                unused -= p[i].r;
                unused += p[i].l;
           }
           printf("%d
    ",ans*2);
        }
        return 0;
    }
    /*
    2
    1
    )()(()(
    2
    )
    )(
    */
    
  • 相关阅读:
    5 float f = 3.4,是否正确
    4 String是基本数据类型吗
    3 访问修饰符public,private,protected以及不写(默认)时的区别
    1 请谈谈面向对象的三大特征?
    接口和抽象类有什么区别
    2 Java中 == 和 equals 和 hashCode 的区别
    java中重载(overload)与重写(override)的区别
    servlet中请求转发(forword)和重定向(redirect)的区别
    团队-项目名称五子棋-团队一阶段互评
    团队-项目名称五子棋-开发环境搭建过程
  • 原文地址:https://www.cnblogs.com/KirinSB/p/9408748.html
Copyright © 2011-2022 走看看