bzoj2806 [Apio2012]dispatching【可并堆】

传送门:http://www.lydsy.com/JudgeOnline/problem.php?id=2809

保存可并堆模版代码。

#include <cstdio>
#include <cstring>
#include <algorithm>

const int maxn = 100005, maxm = 1000000005;

int n, m, fa[maxn], salary[maxn], lead[maxn];
int key[maxn], left[maxn], right[maxn], npl[maxn], cnt, siz[maxn];
int head[maxn], to[maxn], next[maxn], lb;
long long s[maxn], ans;

inline void ist(int aa, int ss) {
	to[lb] = ss;
	next[lb] = head[aa];
	head[aa] = lb;
	++lb;
}
int merge(int A, int B) {
	if (!A) {
		return B;
	}
	if (!B) {
		return A;
	}
	if (key[B] > key[A]) {
		std::swap(A, B);
	}
	right[A] = merge(right[A], B);
	if (npl[right[A]] > npl[left[A]]) {
		std::swap(left[A], right[A]);
	}
	npl[A] = npl[right[A]] + 1;
	s[A] = s[left[A]] + s[right[A]] + key[A];
	siz[A] = siz[left[A]] + siz[right[A]] + 1;
	return A;
}
int dfs(int r) {
	int rt = ++cnt, tr = -666;
	key[rt] = salary[r];
	s[rt] = salary[r];
	siz[rt] = 1;
	for (int j = head[r]; j != -1; j = next[j]) {
		tr = dfs(to[j]);
		rt = merge(rt, tr);
	}
	while (s[rt] > m) {
		rt = merge(left[rt], right[rt]);
	}
	ans = std::max(ans, (long long)lead[r] * (long long)siz[rt]);
	return rt;
}

int main(void) {
	//freopen("in.txt", "r", stdin);
	memset(head, -1, sizeof head);
	memset(next, -1, sizeof next);
	npl[0] = -1;
	scanf("%d%d", &n, &m);
	for (int i = 1; i <= n; ++i) {
		scanf("%d%d%d", fa + i, salary + i, lead + i);
		ist(fa[i], i);
	}

	dfs(1);
	printf("%lld\n", ans);
	return 0;
}

  

时间: 2024-11-15 15:25:38

bzoj2806 [Apio2012]dispatching【可并堆】的相关文章

[bzoj2809][Apio2012][dispatching] (可并堆)

Description 在一个忍者的帮派里,一些忍者们被选中派遣给顾客,然后依据自己的工作获取报偿.在这个帮派里,有一名忍者被称之为 Master.除了 Master以外,每名忍者都有且仅有一个上级.为保密,同时增强忍者们的领导力,所有与他们工作相关的指令总是由上级发送给他的直接下属,而不允许通过其他的方式发送.现在你要招募一批忍者,并把它们派遣给顾客.你需要为每个被派遣的忍者 支付一定的薪水,同时使得支付的薪水总额不超过你的预算.另外,为了发送指令,你需要选择一名忍者作为管理者,要求这个管理者

BZOJ 2809 [Apio2012]dispatching 可并堆

题意:链接 方法:可并堆 解析: 水题,但注意过程爆int. 方法就是找到树的根节点,之后扫,将每个子树什么的看做一个堆,然后之间合并,如果堆中的sum和超过了m,则去掉最大的,继续添加,这个显然啊. 然后每次处理完一个点,用堆中解更新答案. 比前两道水 代码: #include <cstdio> #include <cstring> #include <iostream> #include <algorithm> #define N 100100 usin

bzoj2809[Apio2012]dispatching

bzoj2809[Apio2012]dispatching 题意: n个点组成一棵树,每个点都有一个领导力和费用,可以让一个点当领导,然后在这个点的子树中选择一些费用之和不超过m的点,得到领导的领导力乘选择的点的个数(领导可不被选择)的利润.求利润最大值.n≤100000 题解: 可并堆.可以得到一个结论,就是在子树中选点的时候,先选所有点,如果费用超了,就不断把费用最大的剔除,知道费用不超,这样得到的选点数量最大,这过程可以用堆维护.同时每个点的堆都可以由子树的堆合并得到,所以需要可并堆. 代

[Apio2012]dispatching

[Apio2012]dispatching 时间限制: 1 Sec  内存限制: 128 MB 题目描述 在一个忍者的帮派里,一些忍者们被选中派遣给顾客,然后依据自己的工作获取报偿.在这个帮派里,有一名忍者被称之为 Master.除了 Master以外,每名忍者都有且仅有一个上级.为保密,同时增强忍者们的领导力,所有与他们工作相关的指令总是由上级发送给他的直接下属,而不允许通过其他的方式发送.现在你要招募一批忍者,并把它们派遣给顾客.你需要为每个被派遣的忍者 支付一定的薪水,同时使得支付的薪水总

【BZOJ 2809】2809: [Apio2012]dispatching (左偏树)

2809: [Apio2012]dispatching Description 在一个忍者的帮派里,一些忍者们被选中派遣给顾客,然后依据自己的工作获取报偿.在这个帮派里,有一名忍者被称之为 Master.除了 Master以外,每名忍者都有且仅有一个上级.为保密,同时增强忍者们的领导力,所有与他们工作相关的指令总是由上级发送给他的直接下属,而不允许通过其他的方式发送.现在你要招募一批忍者,并把它们派遣给顾客.你需要为每个被派遣的忍者 支付一定的薪水,同时使得支付的薪水总额不超过你的预算.另外,为

BZOJ 2809 APIO2012 dispatching Treap+启示式合并 / 可并堆

题目大意:给定一棵树,选定一棵子树中的一些点,薪水和不能超过m,求点的数量*子树根节点的领导能力的最大值 考虑对于每一个节点,我们维护一种数据结构,在当中贪心寻找薪金小的雇佣. 每一个节点暴力重建一定不行.我们考虑可并数据结构.每一个节点将子节点的信息直接合并就可以 能够用启示式合并的Treap.也能够用可并堆 今天特意去学了这玩应0.0 先写了左偏树 然后又写了下随机堆-- 后者速度上更快一些 只是建议从左偏树開始学起 总之平衡树常数各种大就是了0.0 Treap+启示式合并 #include

【bzoj2809】[Apio2012]dispatching 贪心+可并堆

题目描述 在一个忍者的帮派里,一些忍者们被选中派遣给顾客,然后依据自己的工作获取报偿.在这个帮派里,有一名忍者被称之为 Master.除了 Master以外,每名忍者都有且仅有一个上级.为保密,同时增强忍者们的领导力,所有与他们工作相关的指令总是由上级发送给他的直接下属,而不允许通过其他的方式发送.现在你要招募一批忍者,并把它们派遣给顾客.你需要为每个被派遣的忍者 支付一定的薪水,同时使得支付的薪水总额不超过你的预算.另外,为了发送指令,你需要选择一名忍者作为管理者,要求这个管理者可以向所有被派

BZOJ 2809 APIO2012 dispatching Treap+启发式合并 / 可并堆

题目大意:给定一棵树,选定一棵子树中的一些点,薪水和不能超过m,求点的数量*子树根节点的领导能力的最大值 考虑对于每个节点,我们维护一种数据结构,在其中贪心寻找薪金小的雇佣. 每个节点暴力重建一定不行,我们考虑可并数据结构,每个节点将子节点的信息直接合并即可 可以用启发式合并的Treap,也可以用可并堆 今天特意去学了这玩应0.0 先写了左偏树 然后又写了下随机堆-- 后者速度上更快一些 不过建议从左偏树开始学起 总之平衡树常数各种大就是了0.0 Treap+启发式合并 #include<cst

[BZOJ 2809][Apio2012]dispatching(左偏树)

Description 在一个忍者的帮派里,一些忍者们被选中派遣给顾客,然后依据自己的工作获取报偿.在这个帮派里,有一名忍者被称之为 Master.除了 Master以外,每名忍者都有且仅有一个上级.为保密,同时增强忍者们的领导力,所有与他们工作相关的指令总是由上级发送给他的直接下属,而不允许通过其他的方式发送.现在你要招募一批忍者,并把它们派遣给顾客.你需要为每个被派遣的忍者 支付一定的薪水,同时使得支付的薪水总额不超过你的预算.另外,为了发送指令,你需要选择一名忍者作为管理者,要求这个管理者