[破碎的状态] ARC063E
link:http://arc063.contest.atcoder.jp/tasks/arc063_c
题意:
给你一颗树,有些点有初始权值
现在求一个方案(当然如果不存在方案输出No即可)(如果方案存在,输出Yes)
把所有点都赋一个权值,每条边的权值差恰好为1
(原来有权值就不能改了)
解法:
我们随便找个根
有一个性质,就是一个点的取值范围恰好是一个区间内所有的奇数/偶数
证明不太会,但是看起来是挺对的....
那么就是,每个点是不是在取值范围里面...就行了....
如果不是就No掉
如果都是,就Yes
方案的话,我们把根当成它的l值
然后dfs下去
每个如果l可以就l,不可以就r
这样就过了
证明.....不会!
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 | #include<set> #include<map> #include<list> #include<queue> #include<stack> #include<string> #include<math.h> #include<time.h> #include<vector> #include<bitset> #include<memory> #include<utility> #include<fstream> #include<stdio.h> #include<sstream> #include<iostream> #include<stdlib.h> #include<string.h> #include<algorithm> using namespace std; bool flag; struct edge { int y; edge * next; }; edge * li[100005]; edge * new_edge() { static edge a[200005]; static int top=0; return &a[top++]; } void inserts( int x, int y) { edge * t=new_edge(); t->y=y; t->next=li[x]; li[x]=t; } void insert_edge( int x, int y) { inserts(x,y); inserts(y,x); } int l[100005],r[100005]; int w[100005]; bool vis[100005]; void dfs( int x) { vis[x]= true ; edge * t; for (t=li[x];t!=0;t=t->next) { if (vis[t->y]) continue ; dfs(t->y); l[x]=max(l[x],l[t->y]-1); r[x]=min(r[x],r[t->y]+1); } if (l[x]>r[x]) { flag= true ; } if (w[x]==-1) return ; if (l[x]%2!=w[x]%2) { if (l[x]>-1000000) flag= true ; } if (l[x]>w[x]) { flag= true ; } if (w[x]>r[x]) { flag= true ; } l[x]=w[x]; r[x]=w[x]; } void dfs2( int x, int val) { if (w[x]==-1) { w[x]=val; } vis[x]= false ; edge * t; for (t=li[x];t!=0;t=t->next) { if (vis[t->y]) { int temp=val; if (temp<l[t->y]) temp++; else temp--; dfs2(t->y,temp);; } } } int main() { #ifdef absi2011 freopen ( "input.txt" , "r" ,stdin); freopen ( "output.txt" , "w" ,stdout); #endif int n; scanf ( "%d" ,&n); int i; for (i=1;i<n;i++) { int x,y; scanf ( "%d%d" ,&x,&y); x--; y--; insert_edge(x,y); } int q; scanf ( "%d" ,&q); for (i=0;i<n;i++) { l[i]=-10000000; r[i]=200000000; vis[i]= false ; w[i]=-1; } for (i=0;i<q;i++) { int x,y; scanf ( "%d%d" ,&x,&y); x--; w[x]=y; } flag= false ; dfs(0); if (flag) { puts ( "No" ); return 0; } puts ( "Yes" ); dfs2(0,l[0]); for (i=0;i<n;i++) { printf ( "%d\n" ,w[i]); } return 0; } |