51nod 1273 旅行计划(思维题)
2017-08-18 10:26
351 查看
一开始看到这题真的有点懵逼...一直在想着套算法,结果题解除了sort和dfs其他什么都没用到
显然每次到达的一定都是叶子,先从根节点dfs一遍,按深度对叶子降序排序,按这个顺序向根节点dfs,路径上没有被之前的叶子遍历过的点就是到达这个叶子时未经过的点的个数,于是我们跑出所有叶子未经过点的个数再排序一次输出就行了
#include<iostream> #include<cstdlib> #include<cstring> #include<cstdio> #include<algorithm> #include<queue> #include<cmath> #include<map> #define ll long long using namespace std; const int maxn=500010,inf=1e9; struct tjm{int too,pre;}e[maxn]; struct poi{int w,pos;}a[maxn],b[maxn]; int n,x,tot,cnt,root,t; int last[maxn]; bool v[maxn]; void read(int &k) { int f=1;k=0;char c=getchar(); while(c<'0'||c>'9')c=='-'&&(f=-1),c=getchar(); while(c<='9'&&c>='0')k=k*10+c-'0',c=getchar(); k*=f; } inline bool cmp(poi a,poi b){return a.w==b.w?a.pos<b.pos:a.w>b.w;} inline void add(int x,int y){e[++tot].too=y;e[tot].pre=last[x];last[x]=tot;} inline void dfs(int x,int dep,int fa) { bool flag=0; for(int i=last[x];i;i=e[i].pre) if(e[i].too!=fa)dfs(e[i].too,dep+1,x),flag=1; if((!flag)&&x!=root)a[++cnt].pos=x,a[cnt].w=dep; } inline bool dfs2(int x,int fa) { if(x==root||v[x])return 1; for(int i=last[x];i;i=e[i].pre) if(e[i].too!=fa)if(dfs2(e[i].too,x))return t++,v[x]=1,1; return 0; } int main() { read(n);read(root); for(int i=1;i<n;i++)read(x),add(x,i),add(i,x); dfs(root,0,-1);sort(a+1,a+1+cnt,cmp); for(int i=1;i<=cnt;i++) { t=0;b[i].pos=a[i].pos; dfs2(a[i].pos,-1); b[i].w=t; } sort(b+1,b+1+cnt,cmp); printf("%d\n",root);for(int i=1;i<=cnt;i++)printf("%d\n",b[i].pos); return 0; }View Code
先分析,再做题!
相关文章推荐
- 51nod 1273 旅行计划——思维题
- 【51Nod】1273 旅行计划 树上贪心
- 51Nod-1273-旅行计划
- 51nod 1237 旅行计划(树,贪心)
- 51 nod 1273 旅行计划(树DP)
- 洛谷 P1137 旅行计划
- 51nod 1442 士兵的旅行
- 51nod 1097 拼成最小的数 思维
- 51nod 1770 数数字【模拟+思维】
- 51nod 1266 蚂蚁 【思维题】
- 51nod 1218 最长递增子序列 | 思维题
- 51nod 1393 0和1相等串 (思维+前缀和)
- 51Nod - 1097 思维 + 排序
- 51nod 1421 最大MOD值(思维)
- Problem C A君的旅行计划
- 51nod 1181 质数中的质数(质数筛法)【思维素数】
- 51nod 1413 权势二进制 (思维+贪心)
- 51nod 1099 贪心/思维
- 51Nod 1305 Pairwise Sum and Divide | 思维 数学
- 自在客: 个性化旅行计划定制服务