HDU 4912 Paths on the tree LCA ordering greedy, hdu4912
The path of n m trees is given.
The n-1 line below shows a tree.
Purpose:
Select as many paths as possible in m paths to make the selected paths mutually exclusive.
(Intersection means that a point appears in two or more paths)
Lca...
Sort the order and then make the violence safe
_ (: Too many rows )_
# Pragma comment (linker, "/STACK: 102400000,102400000") # include "cstdio" # include "iostream" # include "set" # include "queue" # include "string. h "using namespace std; # define N 100010 struct Edge {int from, to, nex;} edge [2 * N]; int head [N], edgenum, dis [N], fa [N] [20], dep [N]; // fa [I] [x] is the 2nd ^ x father of I (if the range is exceeded, it is the root) void add (int u, int v) {Edge E = {u, v, head [u]}; edge [edgenum] = E; head [u] = edgenum ++;} void bfs (int root) {queue <int> Q; fa [root] [0] = root; dep [root] = 0; dis [root] = 0; q. push (root); while (! Q. empty () {int u = q. front (); q. pop (); for (int I = 1; I <20; I ++) fa [u] [I] = fa [fa [u] [I-1] [I-1]; for (int I = head [u]; ~ I; I = edge [I]. nex) {int v = edge [I]. to; if (v = fa [u] [0]) continue; dep [v] = dep [u] + 1; dis [v] = dis [u] + 1; fa [v] [0] = u; q. push (v) ;}} int Lca (int x, int y) {if (dep [x] <dep [y]) swap (x, y ); for (int I = 0; I <20; I ++) if (dep [x]-dep [y]) & (1 <I )) x = fa [x] [I]; if (x = y) return x; for (int I = 19; I> = 0; I --) if (fa [x] [I]! = Fa [y] [I]) x = fa [x] [I], y = fa [y] [I]; return fa [x] [0];} void init () {memset (head,-1, sizeof head); edgenum = 0;} int n, m; struct node {int l, r, lca ;} q [N]; bool cmp (node a, node B) {return dep [. lca]> dep [B. lca];} int vis [N], tim; int main () {int I, j, u, v; memset (vis, 0, sizeof vis); tim = 1; while (~ Scanf ("% d", & n, & m) {init (); tim ++; for (I = 1; I <n; I ++) {scanf ("% d", & u, & v); add (u, v); add (v, u);} bfs (1 ); for (I = 1; I <= m; I ++) {scanf ("% d", & q [I]. l, & q [I]. r); q [I]. lca = Lca (q [I]. l, q [I]. r);} sort (q + 1, q + 1 + m, cmp); int ans = 0; for (I = 1; I <= m; I ++) {int lca = q [I]. lca; u = q [I]. l, v = q [I]. r; if (vis [lca] = tim) continue; bool OK = true; if (u = lca) {while (v! = Lca) {if (vis [v] = tim) {OK = false; break;} v = fa [v] [0];} if (OK) {ans ++; v = q [I]. r; while (v! = Lca) {vis [v] = tim; v = fa [v] [0];} vis [lca] = tim ;}} else if (v = lca) {while (u! = Lca) {if (vis [u] = tim) {OK = false; break;} u = fa [u] [0];} if (OK) {ans ++; u = q [I]. l; while (u! = Lca) {vis [u] = tim; u = fa [u] [0];} vis [lca] = tim ;}} else {while (v! = Lca) {if (vis [v] = tim) {OK = false; break;} v = fa [v] [0];} if (OK) while (u! = Lca) {if (vis [u] = tim) {OK = false; break;} u = fa [u] [0];} if (OK) {ans ++; u = q [I]. l, v = q [I]. r; while (v! = Lca) {vis [v] = tim; v = fa [v] [0];} while (u! = Lca) {vis [u] = tim; u = fa [u] [0];} vis [lca] = tim ;}}} cout <ans <endl;} return 0 ;} /* 9 31 21 32 42 53 83 95 65 71 28 96 79 41 21 32 42 53 83 95 65 71 28 96 72 4 */