Link:https://www.lydsy.com/JudgeOnline/problem.php?id=2809

Algorithm:

很容易看出此题贪心的思路:

只要在每个点的子树中贪心选取费用最小的,使其总和不超过m即可

维护最小值,想到用堆,但普通的堆无法进行合并

于是用到数据结构可并堆/左偏树来在O(logN)的时间内合并堆

可并堆和左偏树的区别仅仅在于左偏树多维护了dist数组,而可并堆是无脑交换左右子树

这也使得左偏树的复杂度是能证明的O(logN),而可并堆仅仅是均摊复杂度为O(logN),因此还是尽量用左偏树吧

证明:n个节点的左偏树的距离dist最大为log(n+1)-1

若左偏树的距离为一定值,则节点数最少的左偏树是完全二叉树。

设一棵左偏树的距离为k,则这棵左偏树至少有2^{k+1}-1个节点

因为n>=2^{k+1}-1,所以k<=log(n+1)-1

Code:

左偏树:

  1. #include <bits/stdc++.h>
  2.  
  3. using namespace std;
  4. typedef long long ll;
  5.  
  6. inline int read()
  7. {
  8. char ch;int num,f=;
  9. while(!isdigit(ch=getchar())) f|=(ch=='-');
  10. num=ch-'';
  11. while(isdigit(ch=getchar())) num=num*+ch-'';
  12. return f?-num:num;
  13. }
  14.  
  15. const int MAXN=1e5+;
  16. vector<int> G[MAXN];
  17. struct LTree
  18. {
  19. int ls,rs,dist,val;
  20. ll siz,sum;
  21. }Lt[MAXN];
  22.  
  23. int n,m,C[MAXN],L[MAXN],root[MAXN];
  24. ll res=;
  25.  
  26. int merge(int x,int y)
  27. {
  28. if(!x || !y) return x+y;
  29. if(Lt[x].val<Lt[y].val) swap(x,y);
  30. Lt[x].rs=merge(Lt[x].rs,y);
  31.  
  32. if(Lt[Lt[x].ls].dist<Lt[Lt[x].rs].dist) swap(Lt[x].ls,Lt[x].rs);
  33. Lt[x].dist=Lt[Lt[x].rs].dist+;
  34. Lt[x].siz=Lt[Lt[x].rs].siz+Lt[Lt[x].ls].siz+;
  35. Lt[x].sum=Lt[Lt[x].rs].sum+Lt[Lt[x].ls].sum+Lt[x].val;
  36.  
  37. return x;
  38. }
  39.  
  40. void pop(int &x)
  41. {
  42. x=merge(Lt[x].ls,Lt[x].rs);
  43. }
  44.  
  45. void dfs(int x)
  46. {
  47. root[x]=x;
  48. for(int i=;i<G[x].size();i++)
  49. dfs(G[x][i]),root[x]=merge(root[x],root[G[x][i]]);
  50. while(Lt[root[x]].siz && Lt[root[x]].sum>m) pop(root[x]);
  51. res=max(res,L[x]*Lt[root[x]].siz);
  52. }
  53.  
  54. int main()
  55. {
  56. n=read();m=read();
  57. for(int i=;i<=n;i++)
  58. {
  59. int x=read();G[x].push_back(i);
  60. C[i]=read();L[i]=read();
  61. Lt[i].sum=Lt[i].val=C[i];Lt[i].siz=;
  62. }
  63.  
  64. dfs();
  65. cout << res;
  66. return ;
  67. }

可并堆:

  1. #include <bits/stdc++.h>
  2.  
  3. using namespace std;
  4. typedef long long ll;
  5.  
  6. inline int read()
  7. {
  8. char ch;int num,f=;
  9. while(!isdigit(ch=getchar())) f|=(ch=='-');
  10. num=ch-'';
  11. while(isdigit(ch=getchar())) num=num*+ch-'';
  12. return f?-num:num;
  13. }
  14.  
  15. const int MAXN=1e5+;
  16. vector<int> G[MAXN];
  17.  
  18. int n,m,C[MAXN],L[MAXN],root[MAXN];
  19. ll res=;
  20.  
  21. struct SkewHeap
  22. {
  23. int v[MAXN],ls[MAXN],rs[MAXN];
  24. ll siz[MAXN],sum[MAXN];
  25.  
  26. int merge(int x,int y)
  27. {
  28. if(!x || !y) return x+y;
  29. if(v[x]<v[y]) swap(x,y);
  30. rs[x]=merge(rs[x],y);
  31. swap(ls[x],rs[x]);
  32.  
  33. sum[x]=sum[ls[x]]+sum[rs[x]]+v[x];
  34. siz[x]=siz[ls[x]]+siz[rs[x]]+;
  35. return x;
  36. }
  37.  
  38. void pop(int &x){x=merge(ls[x],rs[x]);}
  39. }Heap;
  40.  
  41. void dfs(int x)
  42. {
  43. root[x]=x;
  44. for(int i=;i<G[x].size();i++)
  45. dfs(G[x][i]),root[x]=Heap.merge(root[x],root[G[x][i]]);
  46. while(Heap.siz[root[x]] && Heap.sum[root[x]]>m) Heap.pop(root[x]);
  47. res=max(res,L[x]*Heap.siz[root[x]]);
  48. }
  49.  
  50. int main()
  51. {
  52. n=read();m=read();
  53. for(int i=;i<=n;i++)
  54. {
  55. int x=read();G[x].push_back(i);
  56. C[i]=read();L[i]=read();
  57. Heap.siz[i]=;Heap.sum[i]=Heap.v[i]=C[i];
  58. }
  59.  
  60. dfs();
  61. cout << res;
  62. return ;
  63. }

Review:

1、对于每棵左偏树,最好用root[x]记录其根节点

2、对于左偏树要跟着维护的信息,

     在merge的最后进行更新

3、可选择将整个数据结构封装在一个类中,写起来可能方便点

[BZOJ 2809] Dispatching的更多相关文章

  1. BZOJ - 2809 dispatching 主席树+dfs序

    在一个忍者的帮派里,一些忍者们被选中派遣给顾客,然后依据自己的工作获取报偿.在这个帮派里,有一名忍者被称之为 Master.除了 Master以外,每名忍者都有且仅有一个上级.为保密,同时增强忍者们的 ...

  2. 【BZOJ 2809 dispatching】

    Time Limit: 10 Sec  Memory Limit: 128 MBSubmit: 4393  Solved: 2246[Submit][Status][Discuss] Descript ...

  3. BZOJ 2809: [Apio2012]dispatching( 平衡树 + 启发式合并 )

    枚举树上的每个结点做管理者, 贪心地取其子树中薪水较低的, 算出这个结点为管理者的满意度, 更新答案. 用平衡树+启发式合并, 时间复杂度为O(N log²N) ------------------- ...

  4. bzoj 2809: [Apio2012]dispatching -- 可并堆

    2809: [Apio2012]dispatching Time Limit: 10 Sec  Memory Limit: 128 MB Description 在一个忍者的帮派里,一些忍者们被选中派 ...

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

    2809: [Apio2012]dispatching Description 在一个忍者的帮派里,一些忍者们被选中派遣给顾客,然后依据自己的工作获取报偿.在这个帮派里,有一名忍者被称之为 Maste ...

  6. AC日记——dispatching bzoj 2809

    2809: [Apio2012]dispatching Time Limit: 10 Sec  Memory Limit: 128 MBSubmit: 3290  Solved: 1740[Submi ...

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

    题目大意:给定一棵树,选定一棵子树中的一些点,薪水和不能超过m,求点的数量*子树根节点的领导能力的最大值 考虑对于每一个节点,我们维护一种数据结构,在当中贪心寻找薪金小的雇佣. 每一个节点暴力重建一定 ...

  8. BZOJ 2809: [Apio2012]dispatching(左偏树)

    http://www.lydsy.com/JudgeOnline/problem.php?id=2809 题意: 思路:最简单的想法就是枚举管理者,在其子树中从薪水低的开始选起,但是每个节点都这样处理 ...

  9. BZOJ 2809 [Apio2012]dispatching(斜堆+树形DP)

    [题目链接] http://www.lydsy.com/JudgeOnline/problem.php?id=2809 [题目大意] 给出一棵树,求出每个点有个权值,和一个乘算值,请选取一棵子树, 并 ...

随机推荐

  1. mysql5.7.22以上版本忘记密码时这样修改

    1.关闭mysql服务 net stop mysql 2.找到mysql安装路径找到 my.ini 打开在 [mysqld] 下添加 skip-grant-tables 跳过密码校验 3.登陆mysq ...

  2. 如何在plsql/developer的命令窗口执行sql脚本

    在plsql/developer的命令窗口执行sql脚本的命令是@+路径 示例如下: 第一步:在C:\Users\linsenq\Desktop目录下新建一个脚本文件: test.sql test.s ...

  3. 用filters定制化spring的包扫描

    Fiter的信息如下: Filter的类型有:annotation(这是spring默认的),assignable,aspectj, regex,custom 首先看一下我这个demo的目录结构: 上 ...

  4. HTTP中的URL长度限制

    首先,其实http 1.1 协议中对url的长度是不受限制的,协议原文: The HTTP protocol does not place any a priori limit on the leng ...

  5. bzoj 5028: 小Z的加油店——带修改的区间gcd

    Description 小Z经营一家加油店.小Z加油的方式非常奇怪.他有一排瓶子,每个瓶子有一个容量vi.每次别人来加油,他会让 别人选连续一段的瓶子.他可以用这些瓶子装汽油,但他只有三种操作: 1. ...

  6. [POJ1595]欧拉线性筛(虽然这道题不需要...)

    欧拉线性筛. 对于它的复杂度的计算大概思考了很久. procedure build_prime; var i,j:longint; begin fillchar(vis,sizeof(vis),tru ...

  7. 对象是否拥有某个属性,in和for in以及object.hasOwnProperty('×××')的异同,以及Object.defineProperty(),Object.keys(),Object.getOwnPropertyNames()的用法

    1.在某个对象是否拥有某个属性,判断的方法有很多,常用的方法就是object.hasOwnProperty('×××'),这个方法是不包括对象原型链上的方法的,举个例子: var obj = { na ...

  8. [ Openstack ] OpenStack-Mitaka 高可用之 镜像服务(glance)

    目录 Openstack-Mitaka 高可用之 概述    Openstack-Mitaka 高可用之 环境初始化    Openstack-Mitaka 高可用之 Mariadb-Galera集群 ...

  9. WCF测试小程序

    using System;using System.Collections.Generic;using System.Linq;using System.Runtime.Serialization;u ...

  10. 【LeetCode】Reverse digits of an integer

    Reverse digits of an integer. Example1: x = 123, return 321Example2: x = -123, return -321 Have you ...