• CodeForces 149D Coloring Brackets


    题目链接: http://codeforces.com/contest/149/problem/D

    -----------------------------------------------------------------------------------------------

    半年前这道区间$DP$磨叽了一天不会 现在感觉是很多地方的题解没写清楚 自己多想会就好了

    首先我们用$F[L][R][c1][c2]$表示从$L$到$R$这段区间左右端点颜色分别为$c1,c2$的方案数

    $($颜色为$0$代表无色$)$然后用记忆化搜索求解

    做的过程中要分两种情况进行讨论

    $1.$若$L,R$为匹配的括号 则对区间$[L + 1,R - 1]$进行讨论

    2.否则对$[L,m[L]],[m[L] + 1, R]$进行讨论$(m$为该左括号匹配的右括号位置$)$

    最后对于$L + 1= R$的区间特判即可

    -----------------------------------------------------------------------------------------------

     1 #include <cstdio>
     2 #include <cstring>
     3 #include <cmath>
     4 #include <algorithm>
     5 using namespace std;
     6 const int N = 710, mod = 1e9 + 7;
     7 char s[N];
     8 long long f[N][N][3][3];
     9 bool check[3][3] = {{0, 1, 1},{1, 0, 0},{1, 0, 0}};
    10 bool check2[3][3] = {{1, 1, 1},{1, 0, 1},{1, 1, 0}};
    11 int m[N], st[N];
    12 int n, top;
    13 long long ans = 0;
    14 long long dfs(int L, int R, int c1, int c2)
    15 {
    16     if(f[L][R][c1][c2] != -1)
    17         return f[L][R][c1][c2];
    18     f[L][R][c1][c2] = 0;
    19     if(m[L] == R)
    20     {
    21         if(!check[c1][c2])
    22             return 0;
    23         if(L + 1 == R)
    24             return f[L][R][c1][c2] = 1;
    25         for(int i = 0; i < 3; ++i)
    26             for(int j = 0; j < 3; ++j)
    27                 if(check2[c1][i] && check2[j][c2])
    28                     f[L][R][c1][c2] = (f[L][R][c1][c2] + 
    29                     dfs(L + 1, R - 1, i, j)) % mod;
    30     }
    31     else
    32     {
    33         for(int i = 0; i < 3; ++i)
    34             for(int j = 0; j < 3; ++j)
    35             {
    36                 if(check2[i][j] && check[c1][i])
    37                     f[L][R][c1][c2] = (f[L][R][c1][c2] + 
    38                     dfs(L, m[L], i, c1) * dfs(m[L] + 1, R, c2, j)) % mod;
    39             }
    40     }
    41     return f[L][R][c1][c2];
    42 }
    43 int main()
    44 {
    45     scanf("%s", s + 1);
    46     n = strlen(s + 1);
    47     for(int i = 1; i <= n; ++i)
    48         if(s[i] == '(')
    49             st[top ++] = i;
    50         else
    51             m[st[-- top]] = i;
    52     memset(f, -1, sizeof f);
    53     for(int i = 0 ; i < 3; ++i)
    54         for(int j = 0; j < 3; ++j)
    55             ans += dfs(1, n, i, j);
    56     printf("%lld
    ", ans % mod);
    57     return 0;
    58 }
  • 相关阅读:
    Django的FBV和CBV
    爬虫-----selenium模块自动爬取网页资源
    python摸爬滚打之day33----线程
    python摸爬滚打之day032 管道 数据共享 进程池
    python摸爬滚打之day030----进程
    爬虫重复请求超时
    指定页面刷新时间前端
    requests post请求,加上会话功能 以及url 编码问题
    爬虫常用mysql
    python操作excel以及word文档,pdf文档
  • 原文地址:https://www.cnblogs.com/sagitta/p/5176390.html
Copyright © 2020-2023  润新知