题意:

给定一棵树,每次可以拆掉一个树上度数为偶数的点,拆掉该点后,与该点所连的所有边都会被删掉。问,是否有一种删点顺序可以删掉所有的点。如果有,则输出任意一组解。

数据范围:线性做法 O(n)O(n)O(n)

不妨从叶子节点开始考虑问题。不难证明,距叶子节点最近的一个偶点一定要在删除父节点之前被删掉,因为如果先删除父节点则原偶点及其子树中所有点的度数都会是基数。

值得注意的是,每次选择的一定是深度最大的叶节点,所以我们要在 dfsdfsdfs 序上进行操作

我们可以在树的 dfsdfsdfs 序上进行操作。然后对第一个偶点进行 dfsdfsdfs,dfsdfsdfs 的过程中将所有偶点加入到答案队列中,并将第一个找到的偶点与父节点分离。这样,父节点有成为了全新的叶节点,并如此反复下去即可。

时间复杂度为 O(n)O(n)O(n)。

Code:

#include<cstdio>
#include<stack>
#include<queue>
using namespace std;
const int maxn = 500000 + 5;
int head[maxn], to[maxn << 1], nex[maxn << 1], cnt, degree[maxn], parent[maxn], vis[maxn];
stack<int>dfs; queue<int> answer;
inline void add_edge(int u,int v)
{
nex[++cnt] = head[u];
head[u] = cnt;
to[cnt] = v;
}
void dfs1(int u,int fa)
{
dfs.push(u); parent[u] = fa;
for(int v = head[u]; v ; v = nex[v]) if(to[v] != fa) dfs1(to[v], u);
}
void dfs2(int u)
{
answer.push(u); vis[u] = 1;
for(int v = head[u]; v ; v = nex[v]){
--degree[to[v]];
if(to[v] == parent[u] || vis[to[v]]) continue;
if(degree[to[v]] % 2 == 0) dfs2(to[v]);
}
}
int main()
{ int n; scanf("%d",&n);
for(int i = 1;i <= n; ++i){ int a; scanf("%d",&a); if(a == 0) continue; add_edge(i,a); add_edge(a,i); ++degree[a], ++degree[i]; }
dfs1(1, 0);
while(dfs.size())
{
int u = dfs.top(); dfs.pop();
if(degree[u] % 2 == 0) dfs2(u);
}
if(answer.size() == n)
{
printf("YES\n");
while(!answer.empty()){ printf("%d\n",answer.front()); answer.pop();}
}
else printf("NO");
return 0;
}

D. Destruction of a Tree_dfs序_性质分析_思维题的更多相关文章

  1. BZOJ 1108: [POI2007]天然气管道Gaz 性质分析_小结论_巧妙

    Description Mary试图控制成都的天然气市场.专家已经标示出了最好的天然气井和中转站在成都的地图.现在需要将中转 站和天然气井连接起来.每个中转站必须被连接到正好一个钻油井,反之亦然. M ...

  2. CF1168B Good Triple 性质分析_好题

    题意翻译 给出01串s,求数对[l,r]个数,使得能找到至少一对[x,k],使1<=x,k<=|s|且l<=x<x+2k<=r且s[x]=s[x+k]=s[x+2k] 题 ...

  3. cb34a_c++_STL_算法_查找算法_(7)_lower_bound

    cb34a_c++_STL_算法_查找算法_(7)_lower_bound//针对已序区间的查找算法,如set,multiset关联容器-自动排序lower_bound()--第一个可能的位置uppe ...

  4. cb33a_c++_STL_算法_查找算法_(6)binary_search_includes

    cb33a_c++_STL_算法_查找算法_(6)binary_search_includes//针对已序区间的查找算法,如set,multiset关联容器-自动排序binary_search(b,e ...

  5. cb32a_c++_STL_算法_查找算法_(5)adjacent_find

    cb32a_c++_STL_算法_查找算法_(5)adjacent_findadjacent_find(b,e),b,begin(),e,end()adjacent_find(b,e,p),p-par ...

  6. cb28a_c++_STL_算法_查找算法_(1)find_find_if

    cb28a_c++_STL_算法_查找算法_(1)find_find_iffind() //线性查找,比较慢.pos1 = find(ilist.begin(), ilist.end(), 5);fi ...

  7. 日志分析_使用shell完整日志分析案例

    一.需求分析 1. 日志文件每天生成一份(需要将日志文件定时上传至hdfs) 2. 分析日志文件中包含的字段:访问IP,访问时间,访问URL,访问状态,访问流量 3. 现在有"昨日" ...

  8. Spring_MVC_教程_快速入门_深入分析

    Spring MVC 教程,快速入门,深入分析 博客分类: SPRING Spring MVC 教程快速入门  资源下载: Spring_MVC_教程_快速入门_深入分析V1.1.pdf Spring ...

  9. 基于samba实现win7与linux之间共享文件_阳仔_新浪博客

    基于samba实现win7与linux之间共享文件_阳仔_新浪博客 然后启动samba执行如下指令: /dev/init.d/smb start 至此完成全部配置.

随机推荐

  1. buddyinfo 内存碎片数据采集

    不说了,上工具 #cat buddyinfo.sh #!/bin/sh #*************************************************************** ...

  2. linux chattr用法

    在linux中,我们有的时候发现linux无法删除一个文件或者目录. huskiesir第一次遇见这个问题还是在一次服务器被不法分子入侵之后的事情,我就发现某个进程很多,根据进程的名字,我搜索关键字找 ...

  3. ThinkPHP3.1.3分表状态时候的自动验证的代码BUG

    问题描述 ThinkPHP3.1.3 当使用TP的分库分表后 有些地方需要使用Model自动验证create,当验证唯一性unique会出现BUG, 具体描述 因为自动验证检测唯一性会使用隐式的使用f ...

  4. 2019-04-03 Anaconda+VSCode搭建python开发环境,并连接GIthub

    1.最好的Python开发环境 :Anaconda+VSCode搭建python开发环境,conda提供了python开发环境和大量的你不用安装的库 conda的环境变量: 直接在conda 中下载启 ...

  5. MVC笔记(一)

    1 MVC介绍 MVC是一个编程思想. 是一种设计模式 思想: 将一个功能分解成3个部分, M: Model (模型) 处理数据相关的逻辑 V: View (视图) 显示页面 C: Controlle ...

  6. FreeMarker 语法 访问 pojo 的属性

    一.java 代码 @Test public void testFreeMarker() throws Exception { //1.创建一个模板文件 //2.创建一个Configuration对象 ...

  7. 引用内部函数绑定机制,R转义字符,C++引用,别名,模板元,宏,断言,C++多线程,C++智能指针

     1.引用内部函数绑定机制 #include<iostream> #include<functional> usingnamespacestd; usingnamespac ...

  8. muduo总结

    总结说的有的过大,算是对自己学习的一个总结.兴许会不断补充. 模型总结 muduo是基于非堵塞的IO和事件驱动的网络库. muduo的总体结构时one loop per thread+threadpo ...

  9. linux中设置TAB键的宽度

    对于编程的人员来说,常常须要排版代码,这时候就须要TAB键,但TAB键的宽度太大,非常有可能代码太长,延伸到下一行,这个时候你就须要设置TAB键的宽度了. linux下设置TAB键的宽度,做法例如以下 ...

  10. Android开发之大位图压缩水印处理

    我们在发微博或者csdn博文的时候都能够给图片加上一个水印.一个独立的标识,那是怎么实现的呢?先封装一个BitmapTools封装类.该类要解决的问题是一将突破存储至sdcard中,二给图片加上水印. ...