P3015 [USACO11FEB]最好的括号Best Parenthesis

Posted xiaoyezi-wink

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了P3015 [USACO11FEB]最好的括号Best Parenthesis相关的知识,希望对你有一定的参考价值。

P3015 [USACO11FEB]最好的括号Best Parenthesis

题解

一定要开 long long !!!

技术图片

 

 

 

                技术图片

 

通过阅读英文题面我们知道所给出的字符串是已经匹配好的,所以我们只是计算就好了

 

考虑栈模拟实现,每一个括号都视作一层

设数组 s[ i ] 为栈中第 i 层左括号所积累的得分

技术图片

 

(1)当输入0,也就是入栈一个左括号,那么我们s[ ]数组就往下开拓新的一层

(2)当输入1,也就是入栈一个右括号,当前层为右括号,此时有两种情况:

         <1>  上一层的左括号本身没有得分,也就是我们当前的右括号与最近的也就是上一层的左括号匹配,凑出一个(这样的括号,所以把上一层的左括号出栈,它的贡献值为1,添加到上上层的左括号里(因为上上层左括号可能本身就有得分),有:

技术图片

 

         <2> 上一层的左括号本身有得分,实际上我们当前的右括号并不是与最近的也就是上一层的左括号匹配,而是与上上层的括号匹配,即我们得到 ((括号套括号(灰色括号代表已经出栈消掉了),所以内部括号得分*2添加到上上一层左括号里,有:

技术图片

 

 注意上一层的左括号出栈时候清空其得分

 

 

代码

#include<iostream>
#include<cstdio>
#include<cstdlib>
#include<algorithm>
#include<cmath>
#include<string>
#include<cstring>
#include<queue>

using namespace std;

typedef long long ll;

inline int read()
{
    int ans=0;
    char last= ,ch=getchar();
    while(ch<0||ch>9) last=ch,ch=getchar();
    while(ch>=0&&ch<=9) ans=ans*10+ch-0,ch=getchar();
    if(last==-) ans=-ans;
    return ans;
}

const int maxn=1e5+10;
const ll mod=12345678910;
int x,n;
ll s[maxn],top=0;

int main()
{
    n=read();
    for(int i=1;i<=n;i++){
        x=read();
        if(!x) top++;
        else{
            if(s[top]==0) s[top-1]=(s[top-1]+1)%mod,top--;
            else{
                s[top-1]=(s[top-1]+s[top]*2)%mod,s[top]=0,top--;
            }
        }
    }
    printf("%lld
",s[0]);
    return 0;
}

 

以上是关于P3015 [USACO11FEB]最好的括号Best Parenthesis的主要内容,如果未能解决你的问题,请参考以下文章

洛谷 P3014 [USACO11FEB]牛线Cow Line

[USACO11FEB] Cow Line

洛谷P3014 [USACO11FEB]牛线Cow Line

luoguP3014 [USACO11FEB]牛线Cow Line

P1118 [USACO06FEB]数字三角形`Backward Digit Su`… 回溯法

P1118 [USACO06FEB]数字三角形`Backward Digit Su`…