POJ 3162 Walking Race——树形dp+尺取+线段树

网友投稿 528 2022-11-28

POJ 3162 Walking Race——树形dp+尺取+线段树

POJ 3162 Walking Race——树形dp+尺取+线段树

RMQ蜜汁MLE??可能是写挫了,不过尺取+线段是nlogn就过了

#include #include #include #include using namespace std;const int INF = 0x3f3f3f3f;const int maxn = 1e6 + 10;int n, m, tot, head[maxn], dp[maxn][3], x[maxn];struct Edge { int to, cost, next;}edge[maxn<<1];void init() { tot = 0; memset(head, -1, sizeof(head));}void addedge(int u, int v, int cost) { ++tot; edge[tot].to = v, edge[tot].cost = cost, edge[tot].next = head[u]; head[u] = tot;}void dfs1(int u, int p) { for (int i = head[u]; i != -1; i = edge[i].next) { int v = edge[i].to; if (v == p) continue; dfs1(v, u); } int pos = 0; for (int i = head[u]; i != -1; i = edge[i].next) { int v = edge[i].to, cost = edge[i].cost; if (v == p) continue; if (dp[u][0] < dp[v][0] + cost) { dp[u][0] = dp[v][0] + cost; pos = v; } } for (int i = head[u]; i != -1; i = edge[i].next) { int v = edge[i].to, cost = edge[i].cost; if (v == p || v == pos) continue; dp[u][1] = max(dp[u][1], dp[v][0] + cost); }}void dfs2(int u, int p) { for (int i = head[u]; i != -1; i = edge[i].next) { int v = edge[i].to, cost = edge[i].cost; if (v == p) continue; dp[v][2] = max(dp[u][2], ((dp[v][0] + cost == dp[u][0]) ? dp[u][1] : dp[u][0])) + cost; dfs2(v, u); }}struct SegTree { int val[2][maxn<<2]; void pushup(int root) { val[0][root] = max(val[0][root<<1], val[0][root<<1|1]); val[1][root] = min(val[1][root<<1], val[1][root<<1|1]); } void build(int l, int r, int root) { if (l == r) { val[0][root] = max(dp[l][0], dp[l][2]); val[1][root] = max(dp[l][0], dp[l][2]); return; } int mid = (l + r)>>1; build(l, mid, root<<1); build(mid + 1, r, root<<1|1); pushup(root); } int query(int l, int r, int root, int ql, int qr, int index) { if (ql <= l && r <= qr) return val[index][root]; int mid = (l + r)>>1; int ans; if (index == 0) ans = 0; else ans = INF; if (ql <= mid) { if (index == 0) { ans = max(ans, query(l, mid, root<<1, ql, qr, index)); } else { ans = min(ans, query(l, mid, root<<1, ql, qr, index)); } } if (mid < qr) { if (index == 0) { ans = max(ans, query(mid + 1, r, root<<1|1, ql, qr, index)); } else { ans = min(ans, query(mid + 1, r, root<<1|1, ql, qr, index)); } } return ans; }}segtree;int solve() { for (int i = 1; i <= n; i++) x[i] = max(dp[i][0], dp[i][2]); int l = 1, r = 0, maxv = 0, minv = INF, ans = 0; for (int i = 1; i <= n; i++) { r++; maxv = max(maxv, x[i]), minv = min(minv, x[i]); while (l <= r && maxv - minv > m) { l++; maxv = segtree.query(1, n, 1, l, r, 0); minv = segtree.query(1, n, 1, l, r, 1); } ans = max(ans, r - l + 1); } return ans;}int main() { int v, cost; while (~scanf("%d %d", &n, &m)) { init(); for (int i = 1; i <= n - 1; i++) { scanf("%d %d", &v, &cost); addedge(i + 1, v, cost); addedge(v, i + 1, cost); } memset(dp, 0, sizeof(dp)); dfs1(1, -1); dfs2(1, -1); segtree.build(1, n, 1); printf("%d\n", solve()); } return 0;}

版权声明:本文内容由网络用户投稿,版权归原作者所有,本站不拥有其著作权,亦不承担相应法律责任。如果您发现本站中有涉嫌抄袭或描述失实的内容,请联系我们jiasou666@gmail.com 处理,核实后本网站将在24小时内删除侵权内容。

上一篇:HDU - 3586 Information Disturbing——树形dp
下一篇:非常全面的IReport的使用教程
相关文章

 发表评论

暂时没有评论,来抢沙发吧~