Cells UVALive - 3486(dfs序+手动开栈)

给一棵树,每次每次询问一个点是否是另一个点的祖先?

输入时是每个下标对应节点的儿子的数量

用dfs序 时间戳。。

如果一个点是另一个点的祖先,那么它的两个标记一定在祖先的范围之内

#include <iostream>
#include <cstdio>
#include <sstream>
#include <cstring>
#include <map>
#include <set>
#include <vector>
#include <stack>
#include <queue>
#include <algorithm>
#include <cmath>
#define rap(a, n) for(int i=a; i<=n; i++)
#define MOD 2018
#define LL long long
#define ULL unsigned long long
#define Pair pair<int, int>
#define mem(a, b) memset(a, b, sizeof(a))
#define _  ios_base::sync_with_stdio(0),cin.tie(0)
//freopen("1.txt", "r", stdin);
using namespace std;
const int maxn = 20022000, INF = 0x7fffffff;
int r[maxn], l[maxn], sum[333333], zstack[maxn];
bool vis[maxn];
int dfs_clock, top, k, n, m, x, y;
void dfs()
{
    mem(vis, 0);
    dfs_clock = zstack[top=1] = 0;
    while(top > 0)
    {
        k = zstack[top];    //stack里存了结点  赋值给k后 k及对应了输入时的下标 即如果k<n 可以判定是否在输入的时候说了它有几个儿子
        if(!vis[k])
        {
            vis[k] = 1, l[k] = ++dfs_clock;
            if(k < n)
                for(int i=k==0?1:sum[k-1]+1; i<=sum[k]; i++) zstack[++top] = i;
        }
        else
            r[k] = ++dfs_clock, top--;
    }
}

int main()
{
    int T, kase = 0;
    scanf("%d", &T);
    while(T--)
    {
        scanf("%d", &n);
        for(int i=0; i<n; i++)
        {
            int tmp;
            scanf("%d", &tmp);
            sum[i]=i==0?tmp:sum[i-1] + tmp;   //每个下标对应的前缀和 即为当前节点的最后一个儿子的值
        }
        dfs();
        printf("Case %d:\n", ++kase);
        scanf("%d",&m);
        while (m--){
            scanf("%d%d",&x,&y);
            if (l[x]<l[y] && r[x]>r[y]) puts("Yes");
                else puts("No");
        }
        if(T) cout<<endl;
    }
    return 0;
}

原文地址:https://www.cnblogs.com/WTSRUVF/p/9362127.html

时间: 2024-10-08 07:29:35

Cells UVALive - 3486(dfs序+手动开栈)的相关文章

【手动开栈】【dfs序】【树状数组】【Tarjan】bzoj2819 Nim

考虑树状数组区间修改(只对其子树的答案有影响)点查询,每个点记录的是它到根路径上的权值异或和. 答案时query(L)^query(R)^a[lca]. 这种方法在支持区间加法.减法的树上询问的时候可以避免树链剖分. 可能爆栈,考虑手动开栈.(诶诶Tarjan预处理lca的时候怎么没手动开栈?不要在意^_^) 实际上不会爆的. #include<cstdio> #include<stack> #include<algorithm> #include<queue&g

[欧拉回路+手动开栈] poj 1780 Code

题目链接: http://poj.org/problem?id=1780 Code Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 2037   Accepted: 751 Description KEY Inc., the leading company in security hardware, has developed a new kind of safe. To unlock it, you don't need

HDU 3844 Mining Your Own Business(割点,变形,开栈,经典)

题意:给出一个连通图,要求将某些点涂黑,使得无论哪个点(包括相关的边)撤掉后能够成功使得剩下的所有点能够到达任意一个涂黑的点,颜料不多,涂黑的点越少越好,并输出要涂几个点和有多少种涂法. 思路: 要使得任意撤掉一个点都能使其他点能够到达黑点,那么点双连通分量能保证这点,那么就在同个点双连通分量内涂黑1个点.但是每个[点双连通分量]都涂吗?太浪费颜料了,那就缩点成树,只需要涂叶子即可,那就找度为1的缩点.但是种数呢?叶子内的点除了割点外都是可以涂黑的,因为如果黑色割点被撤掉,那么叶子中的其他点怎么

HDU 3887 Counting Offspring(DFS序求子树权值和)

Problem Description You are given a tree, it's root is p, and the node is numbered from 1 to n. Now define f(i) as the number of nodes whose number is less than i in all the succeeding nodes of node i. Now we need to calculate f(i) for any possible i

【BZOJ3786】星系探索 DFS序+Splay

[BZOJ3786]星系探索 Description 物理学家小C的研究正遇到某个瓶颈. 他正在研究的是一个星系,这个星系中有n个星球,其中有一个主星球(方便起见我们默认其为1号星球),其余的所有星球均有且仅有一个依赖星球.主星球没有依赖星球. 我们定义依赖关系如下:若星球a的依赖星球是b,则有星球a依赖星球b.此外,依赖关系具有传递性,即若星球a依赖星球b,星球b依赖星球c,则有星球a依赖星球c. 对于这个神秘的星系中,小C初步探究了它的性质,发现星球之间的依赖关系是无环的.并且从星球a出发只

【bzoj1146】[CTSC2008]网络管理Network 倍增LCA+dfs序+树状数组+主席树

题目描述 M公司是一个非常庞大的跨国公司,在许多国家都设有它的下属分支机构或部门.为了让分布在世界各地的N个部门之间协同工作,公司搭建了一个连接整个公司的通信网络.该网络的结构由N个路由器和N-1条高速光缆组成.每个部门都有一个专属的路由器,部门局域网内的所有机器都联向这个路由器,然后再通过这个通信子网与其他部门进行通信联络.该网络结构保证网络中的任意两个路由器之间都存在一条直接或间接路径以进行通信. 高速光缆的数据传输速度非常快,以至于利用光缆传输的延迟时间可以忽略.但是由于路由器老化,在这些

bzoj 2819 Nim(BIT,dfs序,LCA)

2819: Nim Time Limit: 20 Sec  Memory Limit: 128 MBSubmit: 1596  Solved: 597[Submit][Status][Discuss] Description 著名游戏设计师vfleaking,最近迷上了Nim.普通的Nim游戏为:两个人进行游戏,N堆石子,每回合可以取其中某一堆的任意多个,可以取完,但不可以不取.谁不能取谁输.这个游戏是有必胜策略的.于是vfleaking决定写一个玩Nim游戏的平台来坑玩家. 为了设计漂亮一点的

HDU - 4366 Successor DFS序 + 分块暴力 or 线段树维护

给定一颗树,每个节点都有忠诚和能力两个参数,随意指定一个节点,要求在它的子树中找一个节点代替它,这个节点要满足能力值大于它,而且是忠诚度最高的那个. 首先,dfs一下,处理出L[i], R[i]表示dfs序,则R[i] - L[i] + 1 就是当前i这个节点拥有的子孙个数. 对于一颗树,dfs的时候,访问节点有先后顺序,那么可以用一个struct node List[maxn];表示这课树中访问的先后顺序. 例如这颗树,我假设是先访问0 --> 3 --> 2 ---> 4 ---&g

Codeforces 570D TREE REQUESTS dfs序+树状数组

链接 题解链接:点击打开链接 题意: 给定n个点的树,m个询问 下面n-1个数给出每个点的父节点,1是root 每个点有一个字母 下面n个小写字母给出每个点的字母. 下面m行给出询问: 询问形如 (u, deep) 问u点的子树中,距离根的深度为deep的所有点的字母能否在任意排列后组成回文串,能输出Yes. 思路:dfs序,给点重新标号,dfs进入u点的时间戳记为l[u], 离开的时间戳记为r[u], 这样对于某个点u,他的子树节点对应区间都在区间 [l[u], r[u]]内. 把距离根深度相