Codeforces Challenge 2020B Kuroni and Simple Strings

题意:

对于一个字符串S,如果前半部分都是'(',后半部分都是')',那么它就是一个简单的字符串。

现在,你被赋予了一个由'('和')'组成的字符串,这个字符串不一定简单。

规定:每次操作可以从原字符串删除一个简单的子序列。

你的目标是找到最小的操作次数,使得剩下的字符串没有任何操作空间。

题解:

没有任何操作空间等价于所有符号全都背靠背)(.

等价于只删除一次,删除最大的简单序列即可。因为删除两次的话,一定可以合并。

所以输出第一行一定是1。

然后输出删除的子序列长度和每个元素的下标即可。

先统计出整个字符串右括号的数量。

然后遍历整个字符串,遇到一个右括号,就把右括号的数量加一,如果遇到左括号,就把左括号的数量减一。

当右括号的数量等于左括号时,就停止遍历,并记录下这个中间点,输出这个中间点左边所有的左括号,输出这个中间点右边所有的右括号。

#include<bits/stdc++.h>
using namespace std;
const int maxn=1014;
string s;
int main () {
    cin>>s;
    int suf=0;
    for (int i=0;i<s.length();i++)
        suf+=s[i]==')';
    int pref=0;
    int cut=-1;
    for (int i=0;i<s.length();i++) {
        if (pref==suf) {
            cut=i;
            break;
        }
        if (s[i]=='(') pref++;
        else suf--;
    }
    vector<int> vi;
    for (int i=0;i<cut;i++)
        if (s[i]=='(') vi.push_back(i);
    for (int i=cut;i<s.length();i++) 
        if (s[i]==')') vi.push_back(i);
    if (vi.empty()) printf("0\n");
    else {
        printf ("1\n");
        printf ("%d\n",vi.size());
        for (int i=0;i<vi.size();i++) {
            if (i) printf (" ");
            printf ("%d",vi[i]+1);
        } 
        printf ("\n");
    }
    return 0;
}

 

posted @ 2020-03-05 19:42  zlc0405  阅读(195)  评论(0编辑  收藏  举报