wc2013|wc2013 糖果公园

【wc2013|wc2013 糖果公园】传送门:http://uoj.ac/problem/58
思路:果断树上莫队模板,果断看的题解,,关于时间作为第三维推来推去idea还是极好的,弄了好久就因为不明白出战入站序的性质,,,反省,而且被vfk讲晕了,,明显他的集合标准差是另一种直接在树上做的写法,还是出战入站序好用,,,本来狂WA不止,,原来是没开LL,改了还是WA,,睡了,,第二天微机课,,改了快的大小,,仍然WA,不得已看了标程,,然而,,,就把一个内容改写成了函数,,就A了,,,什么玩意,,我明明没动程序好吧,,,就是不明白啊,,,貌似还有块状树的做法,有些部分分的做法也是值得借鉴的,,,
未完待续(非常重要)
代码:

#include #include #include #include #include #include #define N 100000 using namespace std; typedef long long LL; struct edge{ int nxt,point,v; }; struct node { int t,x,y,id; LL ans; }; struct data{ int num,last,now; }; edge e[(N<<1)+5]; node que1[(N<<1)+5]; data que2[(N<<1)+5]; int n,m,q,cnt,cnt1,cnt2,time1; int v[N+5],w[N+5],a[N+5],b[N+5],dfn[(N<<1)+5],l[N+5],r[N+5],fa[N+5][25],deep[N+5],pos[(N<<1)+5],ts[N+5]; bool vis[N+5]; LL sum; inline void addedge(int u1,int v1){ e[++cnt].nxt = e[u1].point; e[u1].point = cnt; e[cnt].v = v1; } inline void insert(int u1,int v1){ addedge(u1,v1); addedge(v1,u1); } inline bool cmp(node a,node b){ return ((pos[a.x] < pos[b.x])||(pos[a.x] == pos[b.x]&&pos[a.y]inline bool cmp1(node a,node b){ return (a.id < b.id); } inline int getnum(){ char c; int num; while (!isdigit(c = getchar())); num = c - '0'; while (isdigit(c = getchar())) num = 10 * num + c - '0'; return num; }void init(){ n = getnum(); m = getnum(); q = getnum(); cnt = 0; for (int i = 1; i <= m; ++i) v[i] = getnum(); for (int i = 1; i <= n; ++i) w[i] = getnum(); for (int i = 1; i < n; ++i){ int u1 = getnum(),v1 = getnum(); insert(u1,v1); } for (int i = 1; i <= n; ++i) a[i] = b[i] = getnum(); time1 = 0; }inline void dfs(int x){ l[x] = ++time1; dfn[time1] = x; for (int i = 1; i <= 20; ++i) fa[x][i] = fa[fa[x][i-1]][i-1]; for (int p = e[x].point; p; p = e[p].nxt) if (!l[e[p].v]) { deep[e[p].v] = deep[x] + 1; fa[e[p].v][0] = x; dfs(e[p].v); } r[x] = ++time1; dfn[time1] = x; }inline int LCA(int u,int v){ if (deep[u] < deep[v]) swap(u,v); int ll = deep[u] - deep[v]; for (int i = 20; i >= 0; --i) if (ll&(1<=0; --i) if (fa[u][i] != fa[v][i]) u = fa[u][i],v = fa[v][i]; if (u != v) return fa[u][0]; return u; }void sort_it(){ int sz = (int)pow(time1, 2.0 / 3.0); for (int i = 1; i <= time1; ++i) pos[i] = i/sz; bool p; int u1,v1; cnt1 = cnt2 = 0; for (int i = 1; i <= q; ++i){ p = getnum(); u1 = getnum(); v1 = getnum(); if (!p) que2[++cnt2].num = u1,que2[cnt2].last = b[u1],que2[cnt2].now = b[u1] = v1; else{ int lca = LCA(u1,v1); if (l[u1] > l[v1]) swap(u1,v1); que1[++cnt1].t = cnt2; que1[cnt1].id = cnt1; if (lca != u1) que1[cnt1].x = r[u1], que1[cnt1].y = l[v1]; else que1[cnt1].x = l[u1],que1[cnt1].y = l[v1]; } } sort(que1 + 1,que1 + cnt1 + 1,cmp); //for (int i = 1; i <= cnt1; ++i) cout< que1[i].t; --j) modify(que2[j].num,que2[j].last); } void make_it(){ memset(vis,0,sizeof(vis)); memset(ts,0,sizeof(ts)); //for (int i = 1; i <= n; ++i) ts[a[i]] ++; que1[0].t = 0; que1[0].x = 1; que1[0].y = 0; sum = 0; for (int i = 1; i <= cnt1; ++i){ change_time(i); //cout= que1[i].x; --j) change(dfn[j]); //for (int j = 1; j <= n; ++j) cout< que1[i].y; --j) change(dfn[j]); //for (int j = 1; j <= n; ++j) cout<

    推荐阅读