上午小测3 T1 括号序列 && luogu P5658 [CSP/S 2019 D1T2] 括号树 题解
前 言:
一直很想写这道括号树。。毕竟是在去年折磨了我4个小时的题。。。。
上午小测3 T1 括号序列
前言:
原来这题是个dp啊。。。这几天出了好几道dp,我都没看出来,我竟然折磨菜。
考试的时候先打了个暴力,然后就开始往容斥上想。。。。
解析:
考虑dp。
令dp[i] 表示以i为结尾的,合法的子串数量。
令match[i] 表示进行括号匹配时,与i匹配的括号的编号。
(以上i都是右括号,如果是左括号置为0即可)
然后,就有: if(match[i]) dp[i]=dp[match[i]-1]+1;
这个转移方程的含义如下:
首先是前面的判断语句。必须是在i有匹配的情况下。
这样就排除了两种不可能的情况,一种是i是左括号,另一种是i是右括号,但在进行括号匹配时,没有与其匹配的左括号。
显然以上两种情况,i都不可能成为一个合法字串的结尾。
然后是要先给dp[i]加上1。这是以match[i]为起点,i为终点的子串的贡献。
其次要加上dp[match[i]-1];
这时分两种情况讨论。
第一种是 s[match[i]-1]==')' : 好丑的图
此时以i为结尾的子串还可能继续向左延伸,只要加上dp[match[i]-1]即可。
另外一种是 s[match[i]-1]=='(':
此时不能继续向左延伸,所以不加,但是因为dp[match[i]-1]是0,所以加上也不会错(主要是这样写起来方便)
说的有些麻烦了,其实还是挺显然的。
代码
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
const int maxn=1000000+10;
#define gc() (p1 == p2 ? (p2 = buf + fread(p1 = buf, 1, 1 << 20, stdin), p1 == p2 ? EOF : *p1++) : *p1++)
#define read() ({ register int x = 0, f = 1; register char c = gc(); while(c < '0' || c > '9') { if (c == '-') f = -1; c = gc();} while(c >= '0' && c <= '9') x = x * 10 + (c & 15), c = gc(); f * x; })
char buf[1 << 20], *p1, *p2;
char s[maxn];
int n,top;
int dp[maxn];
int match[maxn];
ll ans;
struct node{
int pos;
char c;
node(){}
node(int x,char y){
pos=x;
c=y;
}
}Stack[maxn];
void Solve(){
scanf("%s",s+1);
n=strlen(s+1);
Stack[++top]=node(1,s[1]);
for(int i=2;i<=n;++i){
if(s[i]==')'&&Stack[top].c=='('){
node t=Stack[top];
top--;
match[i]=t.pos;
}else Stack[++top]=node(i,s[i]);
}
for(int i=1;i<=n;++i){
if(match[i]){
dp[i]=1+dp[match[i]-1];
}
}
for(int i=1;i<=n;++i) ans+=dp[i];
printf("%lld\n",ans);
}
int main(){
freopen("bracket.in","r",stdin);
freopen("bracket.out","w",stdout);
Solve();
return 0;
}
luogu P5658 [CSP/S 2019 D1T2] 括号树
前言:
其实应该不是很难吧。。。
解析:
和上一道题类似,但不是完全相同废话
所以一定要看清题啊。。。
这次问的是每个字符串的合法子串数量。。。我当成以每个字符结尾的合法字串数量了,直接暴毙。。。
会上面那道题,这个就简单多了。
先令dp[i]表示以i结尾的合法字子串数量,然后求个树上前缀和就行了。
照上个题的思路,改改式子:
if(match[i]) dp[i]=dp[fa[match[i]]]+1
最后。。。
不开long long见祖宗!
代码:
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
const int maxn=500000+10;
#define gc() (p1 == p2 ? (p2 = buf + fread(p1 = buf, 1, 1 << 20, stdin), p1 == p2 ? EOF : *p1++) : *p1++)
#define read() ({ register int x = 0, f = 1; register char c = gc(); while(c < '0' || c > '9') { if (c == '-') f = -1; c = gc();} while(c >= '0' && c <= '9') x = x * 10 + (c & 15), c = gc(); f * x; })
char buf[1 << 20], *p1, *p2;
struct node{
int to,nxt;
}edge[maxn<<1];
int head[maxn],fa[maxn],match[maxn];
ll dp[maxn];
char s[maxn];
struct Node{
int pos;
char c;
Node(){}
Node(int x,char y){
pos=x;
c=y;
}
}Stack[maxn];
int n,cnt,top;
ll ans;
void add(int from,int to){
edge[++cnt].to=to;
edge[cnt].nxt=head[from];
head[from]=cnt;
}
void dfs1(int u){
Node t=Stack[top];
if(t.c=='('&&s[u]==')'){
match[u]=t.pos;
top--;
for(int i=head[u];i;i=edge[i].nxt){
int v=edge[i].to;
if(v==fa[u]) continue;
dfs1(v);
}
Stack[++top]=Node(t.pos,t.c);
}else{
Stack[++top]=Node(u,s[u]);
for(int i=head[u];i;i=edge[i].nxt){
int v=edge[i].to;
if(v==fa[u]) continue;
dfs1(v);
}
top--;
}
}
void dfs2(int u){
if(match[u]) dp[u]=dp[fa[match[u]]]+1;
for(int i=head[u];i;i=edge[i].nxt){
int v=edge[i].to;
if(v==fa[u]) continue;
dfs2(v);
}
}
void dfs3(int u,int f){
dp[u]+=dp[f];
for(int i=head[u];i;i=edge[i].nxt){
int v=edge[i].to;
if(v==fa[u]) continue;
dfs3(v,u);
}
}
void Solve(){
scanf("%d%s",&n,s+1);
for(int i=2;i<=n;++i){
scanf("%d",&fa[i]);
add(i,fa[i]);
add(fa[i],i);
}
dfs1(1);
dfs2(1);
dfs3(1,0);
for(int i=1;i<=n;++i) ans^=(1ll*i*dp[i]);
printf("%lld\n",ans);
}
int main(){
// freopen("brackets.in","r",stdin);
// freopen("brackets.out","w",stdout);
Solve();
return 0;
}
上午小测3 T1 括号序列 && luogu P5658 [CSP/S 2019 D1T2] 括号树 题解的更多相关文章
- 上午小测1 T1 木板 题解
前言: WTCL,居然折磨煎蛋的性质都忘记了,WTCL. 考场上想出来了正解,就差一点就能A掉,挺难受的. 要记住一个数n可能会有一个大于\(\sqrt{n}\)的质因子..我忘记把它加进去了.... ...
- CSP-S 2019 D1T2 括号树
题目链接:[https://www.luogu.com.cn/problem/P5658] 思路: 这道题不难.(为什么我在考场上一点思路也没有??) 假设我们已经处理到树上的节点u(假设1为根节点) ...
- 上午小测1 B.序列 哈希表+数学
题目描述 \(EZ\) 每周一都要举行升旗仪式,国旗班会站成一整列整齐地向前行进. 郭神摄像师想要选取其中一段照下来.他想让这一段中每个人的身高成等比数列,展示出最萌身高差.但他发现这个太难办到了.于 ...
- 括号序列模型--序列dp--U86873 小Y的精灵国机房之旅
括号序列模型及解法 >Codeforces314E◦给定一个长度为n的仅包含左右括号和问号的字符串,将问号变成左括号或右括号使得该括号序列合法,求方案总数.◦例如(())与()()都是合法的括号 ...
- 学长小清新题表之UOJ 31.猪猪侠再战括号序列
学长小清新题表之UOJ 31.猪猪侠再战括号序列 题目描述 大家好我是来自百度贴吧的_叫我猪猪侠,英文名叫\(\_CallMeGGBond\). 我不曾上过大学,但这不影响我对离散数学.复杂性分析等领 ...
- 2017-5-14 湘潭市赛 Parentheses 转化思想+贪心 使括号序列合法的最小花费。满足前面左括号的数量>=有括号的数量。
Parentheses Accepted : Submit : Time Limit : MS Memory Limit : KB Parentheses Bobo has a very long s ...
- 括号序列(区间dp)
括号序列(区间dp) 输入一个长度不超过100的,由"(",")","[",")"组成的序列,请添加尽量少的括号,得到一 ...
- 括号序列(Poj1141)
Poj1141 题目描述: 定义合法的括号序列如下: 1 空序列是一个合法的序列 2 如果S是合法的序列,则(S)和[S]也是合法的序列 3 如果A和B是合法的序列,则AB也是合法的序列 例如:下面的 ...
- 括号序列的dp问题模型
括号序列的dp问题模型 Codeforces314E ◦给定一个长度为n的仅包含左括号和问号的字符串,将问号变成左括号或 右括号使得该括号序列合法,求方案总数. ◦例如(())与()()都是合法的括号 ...
随机推荐
- VUE004. provide与inject的使用(祖先组件隔多层传静态值给子孙组件)
provide和inject可以通过祖先组件隔三层四层甚至隔着九层妖塔传值给子孙组件. 需要注意的是这样的传值方式是非响应式的,需要结合自身的应用场景,比如将上传的限制条件通过父组件传值给子组件的子组 ...
- sticky -- position定位属性sticky值之粘性定位;
sticky简述 sticky 是css定为新增的属性:可以说是相对定位relative和固定定位fixed的结合: 它主要用在对scroll事件的监听上,简单说在滑动过程中,某个元素的距离其父元素的 ...
- [第九篇]——Docker 镜像使用之Spring Cloud直播商城 b2b2c电子商务技术总结
Docker 镜像使用 当运行容器时,使用的镜像如果在本地中不存在,docker 就会自动从 docker 镜像仓库中下载,默认是从 Docker Hub 公共镜像源下载. 下面我们来学习: 1.管理 ...
- k8s标签label
1.给节点设置标签 一遍pod部署选择 kubectl label node 节点名 disktype=ssd kubectl label node master1 disktype=ssd 效果 [ ...
- Shell系列(12)- 预定义变量(5)
预定义变量 作用 $? 常用:最后一次执行的命令的返回状态. 如果这个变量的值为0,证明上一个命令正确执行:如果这个变量的值为非0(具体是哪个数,由命令自己来决定),则证明上一个命令执行不正确了 $$ ...
- 痞子衡嵌入式:MCUBootUtility v3.4发布,支持串行NAND
-- 痞子衡维护的 NXP-MCUBootUtility 工具距离上一个大版本(v3.3.0)发布过去 4 个多月了,这一次痞子衡为大家带来了版本升级 v3.4.0,这个版本主要有几个非常重要的更新需 ...
- docker network 参数
一. 格式 docker network COMMAND 二.COMMAND 讲解 2.1 .docker network connect 格式 docker network connect [OPT ...
- AT2161-[ARC065D]シャッフル/Shuffling【dp】
正题 题目链接:https://www.luogu.com.cn/problem/AT2161 题目大意 长度为\(n\)的\(0/1\)串,\(m\)个区间,你可以按照顺序任意排列区间中的数字,求最 ...
- P4643-[国家集训队]阿狸和桃子的游戏【结论】
正题 题目链接:https://www.luogu.com.cn/problem/P4643 题目大意 给出\(n\)个点\(m\)条边的无向图,两个人轮流选择一个未被选择的点加入点集. 然后每个人的 ...
- C++学习笔记:08 多态性
课程<C++语言程序设计进阶>清华大学 郑莉老师) 基本概念 多态性 具体的讲,在面向对象程序设计中,指同样的方法被不同对象执行时会有不同的执行效果. 多态的实现 绑定机制 绑定是将一个标 ...