zoukankan      html  css  js  c++  java
  • [差分约束][栈] Jzoj P4209 已经没有什么好害怕的了

    Description

    小Y 最近开始学习算法姿势,但是因为小R 非常BB,给了她很多B6 题,所以她觉得自己已经没有什么前途了。于是小R 给了她一些稍微简单的题,让她觉得已经没有什么好害怕的了,其中一道是这样的:
    给定一个长度为n 只包含左括号和右括号的序列,现在小R 想要知道经过每一个位置的合法子串有多少个。
    空串是一个合法的串,如果A 和B 都是合法的串,那么(A) 和AB 都是合法的串。
     

    Input

    第一行输入一个正整数T 表示数据组数。接下来T 行每行一个字符串。

    Output

    对于每组数据,输出一个整数表示答案,令ansi 为经过第i 个位置的子串个数,那么你需要输出(注意是先求余再求和)
     

    Sample Input

    1
    ()()

    Sample Output

    20
    样例解释:
    ans 数组为{2,2,2,2},所以输出20。
     

    Data Constraint

    对于10% 的数据,n<=100
    对于30% 的数据,n <= 1000
    对于60% 的数据,n <= 5 <= 10^4
    对于100% 的数据,n <= 10^6,1 <= T<= 10

    题解

    • 看到括号序列,很容易就想到用栈和查分约束来做
    • 但是这题有点不同,它要求的是每一个括号序列经过的点都要+1,问最后的Σ(经过的括号序列的个数*当前点的位置)
    • 那么这样的做法就有点不同,可以考虑求出每一段括号序列的等级,然后一层层的从大到小的弄下来
    • 也就是什么意思呢,例如()()(),显然这整的是一个合法的括号序列,那么它对序列中的每个位置都是有贡献的,差分约束数组1++,7--
    • 再看()()也是一个合法的括号序列,那么它对序列中的一部分位置是有贡献的1++,5--
    • ()以此类推,那么就是这样去做,然后从大的包含一层层往下做
    • 再用差分约束的思想求出每个点所被经过的合法的括号序列的个数
    • 这样的话最后的ans就很好求了(注意注意注意:最后ans不用取模)

    代码

     1 #include <cstdio>
     2 #include <cstring>
     3 #define N 1000010
     4 #define mo 1000000007
     5 #define ll long long 
     6 using namespace std;
     7 ll T,len,f[N],num1[N],num2[N],k[N],l[N],r[N],ans;
     8 char s[N];
     9 int main()
    10 {
    11     scanf("%lld",&T);    
    12     while (T--)
    13     {
    14         scanf("%s",s+1),len=strlen(s+1);
    15         for (ll i=1;i<=len;i++) if (s[i]=='(') k[++k[0]]=i; else if (k[0]) r[k[k[0]]]=i+1,l[i+1]=k[k[0]--];
    16         for (ll i=len+1;i;i--) num1[l[i]]+=++num1[i];
    17         for (ll i=1;i<=len;i++) num2[r[i]]+=--num2[i];
    18         for (ll i=1;i<=len;i++) f[i]=f[i-1]+num1[i]+num2[i];
    19         for (ll i=1;i<=len;i++) ans=ans+f[i]*i%mo;
    20         printf("%lld
    ",ans);
    21         memset(f,0,sizeof(f)),memset(num1,0,sizeof(num1)),memset(num2,0,sizeof(num2)),
    22         memset(l,0,sizeof(l)),memset(r,0,sizeof(r)),memset(k,0,sizeof(k)),ans=0;
    23     }
    24 }
  • 相关阅读:
    Atitti 图像处理 图像混合 图像叠加 blend 原理与实现
    Atitit Gaussian Blur 高斯模糊 的原理and实现and 用途
    Atitit 图像处理 灰度图片 灰度化的原理与实现
    Atitit (Sketch Filter)素描滤镜的实现  图像处理  attilax总结
    Atitit 实现java的linq 以及与stream api的比较
    Atitit attilax在自然语言处理领域的成果
    Atitit 图像处理 常用8大滤镜效果 Jhlabs 图像处理类库 java常用图像处理类库
    Atitit 图像处理--图像分类 模式识别 肤色检测识别原理 与attilax的实践总结
    Atitit apache 和guava的反射工具
    atitit。企业的价值观 员工第一 vs 客户第一.docx
  • 原文地址:https://www.cnblogs.com/Comfortable/p/10299210.html
Copyright © 2011-2022 走看看