题目大意:

定义一个串:只含有 '( )','[ ]','{ }',3种(6个)字符。

定义 SS 串:

  1. 空串是SS表达式。
  2. 若A是SS表达式,且A串中不含有中括号和大括号,则(A)是SS表达式。
  3. 若A是SS表达式,且A串中不含有大括号,则[A]是SS表达式。
  4. 若A是SS表达式,则{A}是SS表达式。

    定义SS串深度:
  5. 空串深度为0.
  6. 若A可以写成*A'*,其中A‘为SS串,*为任意括号,则\(D(A)=D(A’)+1\)。
  7. 若A可以写成BC的形式,其中B、C均是SS串,则\(D(A)=max\{D(B),D(C) \}\)。

    求由l1个对括号,l2对中括号,l3对大括号,深度为d 构成的SS串的个数。

题解:这是一道字符串上的计数类 dp 问题,一般对于字符串计数类问题都先把字符串划分成若干个独立的部分,即:划分子问题,再进行求解。首先是状态的选择,\(dp[d][i][j][k]\) 表示深度不超过 d,且由 i,j,k 个对应括号构成的SS串的个数,之所以选择深度不超过 d,是因为若选择深度恰好为 d,将很难从子状态转移到当前状态,或者说,要考虑的情况也比较多。转移到状态转移如下:



在看题解时,看到了另一种比较优秀的解释:对于每一个括号序列可以看成是一棵树的 dfs 序列(类似 dfs 序),树的最大深度是 d,求计数。

记忆化搜搜版代码如下

#include <cstdio>
#include <iostream>
#include <algorithm>
#include <memory.h>
using namespace std;
const int mod=11380; int dp[31][11][11][11],l1,l2,l3,d; int dfs(int dep,int x,int y,int z){
int &ans=dp[dep][x][y][z];
if(dep<0)return 0;
if(!dep){
if(x+y+z==0)return 1;
else return 0;
}
if(x+y+z==0)return 1;
if(ans>=0)return ans;
int cnt=0;
for(int i=0;i<x;i++)
for(int j=0;j<=y;j++)
for(int k=0;k<=z;k++)
cnt=(cnt+(long long)dfs(dep-1,i,j,k)*dfs(dep,x-1-i,y-j,z-k))%mod;
for(int j=0;j<y;j++)
for(int k=0;k<=z;k++)
cnt=(cnt+(long long)dfs(dep-1,0,j,k)*dfs(dep,x,y-1-j,z-k))%mod;
for(int k=0;k<z;k++)cnt=(cnt+(long long)dfs(dep-1,0,0,k)*dfs(dep,x,y,z-1-k))%mod;
return ans=cnt;
} int main(){
scanf("%d%d%d%d",&l1,&l2,&l3,&d);
memset(dp,-1,sizeof(dp));
printf("%d\n",(dfs(d,l1,l2,l3)-dfs(d-1,l1,l2,l3)+mod)%mod);
return 0;
}

迭代版代码如下

#include <cmath>
#include <cstdio>
#include <cstring>
#include <iostream>
#include <algorithm>
using namespace std; const int P = 11380;
const int M = 35;
const int N = 15;
int f[N][N][N][M]; int fun(int a, int b, int c, int d) {
if (a + b + c == 0) return 1;
int tmp = 0;
for (int i = 0; i < c; i++)
tmp = (tmp + f[a][b][c - i - 1][d] * f[0][0][i][d - 1]) % P;
for (int i = 0; i < b; i++)
for (int j = 0; j <= c; j++)
tmp = (tmp + f[a][b - i - 1][c - j][d] * f[0][i][j][d - 1]) % P;
for (int i = 0; i < a; i++)
for (int j = 0; j <= b; j++)
for (int k = 0; k <= c; k++)
tmp = (tmp + f[a - i - 1][b - j][c - k][d] * f[i][j][k][d - 1]) % P;
return tmp;
} int main() {
int l1, l2, l3, d;
cin >> l1 >> l2 >> l3 >> d;
f[0][0][0][0] = 1;
for (int i = 0; i <= l1; i++)
for (int j = 0; j <= l2; j++)
for (int k = 0; k <= l3; k++)
for (int l = 1; l <= d; l++)
f[i][j][k][l] = fun(i, j, k, l);
if (d) f[l1][l2][l3][d] = (f[l1][l2][l3][d] - f[l1][l2][l3][d - 1] + P) % P;
cout << f[l1][l2][l3][d] << endl;
return 0;
}

【POJ1187】陨石的秘密的更多相关文章

  1. [POJ1187] 陨石的秘密

    问题描述 公元11380年,一颗巨大的陨石坠落在南极.于是,灾难降临了,地球上出现了一系列反常的现象.当人们焦急万分的时候,一支中国科学家组成的南极考察队赶到了出事地点.经过一番侦察,科学家们发现陨石 ...

  2. Genotype&&陨石的秘密

    Genotype: Genotype 是一个有限的基因序列.它是由大写的英文字母A-Z组成,不同的字母表示不同种类的基因.一个基因可以分化成为一对新的基因.这种分化被一个定义的规则集合所控制.每个分化 ...

  3. 题解 【POJ1187】 陨石的秘密

    解析 考虑到数据范围,其实我们可以用记搜. 设\(f[a][b][c][d]\)表示还剩\(a\)个'{}',\(b\)个"[]",\(c\)个"()",深度\ ...

  4. poj[1187][Noi 01]陨石的秘密

    Description 公元11380年,一颗巨大的陨石坠落在南极.于是,灾难降临了,地球上出现了一系列反常的现象.当人们焦急万分的时候,一支中国科学家组成的南极考察队赶到了出事地点.经过一番侦察,科 ...

  5. POJ 1187 陨石的秘密 (线性DP)

    题意: 公元11380年,一颗巨大的陨石坠落在南极.于是,灾难降临了,地球上出现了一系列反常的现象.当人们焦急万分的时候,一支中国科学家组成的南极考察队赶到了出事地点.经过一番侦察,科学家们发现陨石上 ...

  6. AcWing 317. 陨石的秘密

    1 -> {} 2 -> [] 3 -> () \(f[d][a][b][c]\) 表示 \([i * 2 - 1, j * 2]\) 这段区间 深度为 d \(1\) 有 \(a\ ...

  7. 常规DP专题练习

    POJ2279 Mr. Young's Picture Permutations 题意 Language:Default Mr. Young's Picture Permutations Time L ...

  8. 别人整理的DP大全(转)

    动态规划 动态规划 容易: , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , ...

  9. dp题目列表

    此文转载别人,希望自己能够做完这些题目! 1.POJ动态规划题目列表 容易:1018, 1050, 1083, 1088, 1125, 1143, 1157, 1163, 1178, 1179, 11 ...

随机推荐

  1. Webpack 2 视频教程 005 - Webpack 编译输出日志

    原文发表于我的技术博客 这是我免费发布的高质量超清「Webpack 2 视频教程」. Webpack 作为目前前端开发必备的框架,Webpack 发布了 2.0 版本,此视频就是基于 2.0 的版本讲 ...

  2. SQL Server扩充表字段长度,引发的意外KILLED/ROLLBACK

    这一段时间,因为系统升级,新系统产生的数据长度,比原来的数据长度要长,所以说要扩充一下字段长度. ) --修改字段长度sql 在执行的时候,有这样一个情况. 例如Student表的Name字段长度是n ...

  3. M1/M2总结

    在团队项目中,我是dev之一,负责的部分主要是排序部分. 应该说在团队中大家都各司其职,尤其是PM在组织方面也费了很多心思. 当然我个人因为空间上的距离和团队的联系不是那么密切…… 如同老师所言,这是 ...

  4. qa_model

    [code=python] import os import sys import time import numpy import shelve import theano import thean ...

  5. Golang的panic和recover

    panic 关键字panic的作用是制造一次宕机,宕机就代表程序运行终止,但是已经“生效”的延迟函数仍会执行(即已经压入栈的defer延迟函数,panic之前的). 为什么要制造宕机呢?是因为宕机不容 ...

  6. mybatis批量插入和批量更新

    批量插入数据使用的sql语句是: insert into table (aa,bb,cc) values(xx,xx,xx),(oo,oo,oo) mybatis中mapper.xml的代码如下: & ...

  7. [转帖]ASP.NET Core的Kestrel服务器

    ASP.NET Core的Kestrel服务器 https://cloud.tencent.com/developer/article/1023247 在这篇文章中: 何时使用Kestrel和反向代理 ...

  8. [转帖]速度快散热好 为什么U.2 SSD还没普及?

    速度快散热好 为什么U.2 SSD还没普及?   经典的影视剧中总有那么几位武林高手,江湖上只闻其名,不见其形.今天我们要聊的这位爷,誓要拳打南山M.2,脚踩北海SATA 3!它就是固态硬盘界久负盛名 ...

  9. Angular $scope和$rootScope

    <!DOCTYPE html><html ng-app='myModule'><head lang="en"> <meta charset ...

  10. 第八届蓝桥杯国赛java B组第三题

    标题:树形显示 对于分类结构可以用树形来形象地表示.比如:文件系统就是典型的例子. 树中的结点具有父子关系.我们在显示的时候,把子项向右缩进(用空格,不是tab),并添加必要的连接线,以使其层次关系更 ...