题目

https://leetcode.com/problems/online-election/

题解

我的解法是,用预计算(加强堆,O(nlogn)) + 二分查找(用的自带TreeMap,查找复杂度O(logn))。

实际上,最优解可以达到预计算 O(n),只需要比较当前新元素的 count 与当前最大元素的 count,并更新最大元素即可。

下面来说一下为什么用加强堆。

系统自带的堆,它不能动态修改元素。
就是说,已经入堆的元素,如果参与排序的指标方法变化,它不能自动调整。所以有了加强堆。
对于已经入堆的元素,它的字段发生改变的时候,能够以O(logN)的复杂度调整整个堆。

class TopVotedCandidate {TreeSet<Info> treeSet;public TopVotedCandidate(int[] persons, int[] times) {HeapGreater<Person> heap = new HeapGreater<>((o1, o2) -> {if (o1.count != o2.count) {return o2.count - o1.count;} else {return o2.updatedTime - o1.updatedTime;}});HashMap<Integer, Person> map = new HashMap<>(); // index, persontreeSet = new TreeSet<>((o1, o2) -> o1.time - o2.time);for (int i = 0; i < persons.length; i++) {if (!map.containsKey(persons[i])) {Person p = new Person(1, persons[i], times[i]);map.put(persons[i], p);heap.push(p);} else {Person p = map.get(persons[i]);p.count++;p.updatedTime = times[i];heap.resign(p);}treeSet.add(new Info(heap.peek().index, times[i]));}}public int q(int t) {return treeSet.floor(new Info(-1, t)).index;}
}class Info {int index;int time;public Info(int index, int time) {this.index = index;this.time = time;}
}class Person {int count;int index;int updatedTime;public Person(int count, int index, int updatedTime) {this.count = count;this.index = index;this.updatedTime = updatedTime;}
}/** T一定要是非基础类型,有基础类型需求包一层*/
class HeapGreater<T> {private ArrayList<T> heap;private HashMap<T, Integer> indexMap;private int heapSize;private Comparator<? super T> comp;public HeapGreater(Comparator<T> c) {heap = new ArrayList<>();indexMap = new HashMap<>();heapSize = 0;comp = c;}public T peek() {return heap.get(0);}public void push(T obj) {heap.add(obj);indexMap.put(obj, heapSize);heapInsert(heapSize++);}public void resign(T obj) {heapInsert(indexMap.get(obj));heapify(indexMap.get(obj));}private void heapInsert(int index) {while (comp.compare(heap.get(index), heap.get((index - 1) / 2)) < 0) {swap(index, (index - 1) / 2);index = (index - 1) / 2;}}private void heapify(int index) {int left = index * 2 + 1;while (left < heapSize) {int best = left + 1 < heapSize && comp.compare(heap.get(left + 1), heap.get(left)) < 0 ? (left + 1) : left;best = comp.compare(heap.get(best), heap.get(index)) < 0 ? best : index;if (best == index) {break;}swap(best, index);index = best;left = index * 2 + 1;}}private void swap(int i, int j) {T o1 = heap.get(i);T o2 = heap.get(j);heap.set(i, o2);heap.set(j, o1);indexMap.put(o2, i);indexMap.put(o1, j);}
}

leetcode 911. Online Election | 911. 在线选举(加强堆 + 二分查找)相关推荐

  1. LeetCode 410. 分割数组的最大值(极小极大化 二分查找 / DP)

    文章目录 1. 题目 2. 解题 2.1 二分查找 2.2 DP 1. 题目 给定一个非负整数数组和一个整数 m,你需要将这个数组分成 m 个非空的连续子数组. 设计一个算法使得这 m 个子数组各自和 ...

  2. LeetCode 875. 爱吃香蕉的珂珂(二分查找)

    1. 题目 珂珂喜欢吃香蕉.这里有 N 堆香蕉,第 i 堆中有 piles[i] 根香蕉.警卫已经离开了,将在 H 小时后回来. 珂珂可以决定她吃香蕉的速度 K (单位:根/小时).每个小时,她将会选 ...

  3. LeetCode LCP 12. 小张刷题计划(二分查找)

    1. 题目 为了提高自己的代码能力,小张制定了 LeetCode 刷题计划,他选中了 LeetCode 题库中的 n 道题,编号从 0 到 n-1,并计划在 m 天内按照题目编号顺序刷完所有的题目(注 ...

  4. LeetCode 1870. 准时到达的列车最小时速(二分查找)

    文章目录 1. 题目 2. 解题 2.1 模拟超时 2.2 二分查找 1. 题目 给你一个浮点数 hour ,表示你到达办公室可用的总通勤时间. 要到达办公室,你必须按给定次序乘坐 n 趟列车. 另给 ...

  5. LeetCode 1847. 最近的房间(排序离线计算 + 二分查找)

    文章目录 1. 题目 2. 解题 1. 题目 一个酒店里有 n 个房间,这些房间用二维整数数组 rooms 表示,其中 rooms[i] = [roomIdi, sizei] 表示有一个房间号为 ro ...

  6. LeetCode 1760. 袋子里最少数目的球(二分查找)

    文章目录 1. 题目 2. 解题 1. 题目 给你一个整数数组 nums ,其中 nums[i] 表示第 i 个袋子里球的数目.同时给你一个整数 maxOperations . 你可以进行如下操作至多 ...

  7. LeetCode 528. 按权重随机选择(前缀和+二分查找)

    文章目录 1. 题目 2. 解题 1. 题目 给定一个正整数数组 w ,其中 w[i] 代表下标 i 的权重(下标从 0 开始),请写一个函数 pickIndex ,它可以随机地获取下标 i,选取下标 ...

  8. LeetCode 1642. 可以到达的最远建筑(二分查找 / 优先队列贪心)

    文章目录 1. 题目 2. 解题 2.1 二分查找 2.2 优先队列+贪心 1. 题目 给你一个整数数组 heights ,表示建筑物的高度.另有一些砖块 bricks 和梯子 ladders . 你 ...

  9. LeetCode 778. 水位上升的泳池中游泳(二分查找+dfs)

    文章目录 1. 题目 2. 解题 1. 题目 在一个 N x N 的坐标方格 grid 中,每一个方格的值 grid[i][j] 表示在位置 (i,j) 的平台高度. 现在开始下雨了.当时间为 t 时 ...

最新文章

  1. java calendar与date_Java中date和calendar的用法
  2. Gmail全球大规模宕机
  3. Visual C++ 2011-5-27
  4. oracle10g- emctl start dbconsole 启动问题
  5. 【招聘(北京)】北京华光普泰生物招聘.NET软件开发
  6. oracle进入rman报错,Oracle 11g单实例RMAN恢复到Oracle 11g RAC
  7. HDU2005 第几天?【日期计算】
  8. .NET中的异常处理机制(一)
  9. Uubuntu20.04配置openpose
  10. DirectX11环境配置
  11. OpenKG开源系列 | 面向知识的推理问答编程语言KoPL(清华大学)
  12. linux BT面板的安装
  13. 记一次npm安装依赖奇怪的gyp报python错误
  14. 计算机未响应硬盘,最近电脑打开磁盘或文件夹老程序未响应为什么啊,有什么办法可以解决?...
  15. 7-4 最短路径之Dijkstra(朴素dijkstra打印路径)
  16. 十大领域五大过程组(上):你必须了解的项目管理常识
  17. 利用pandas读取Excel文件数据
  18. 魏文王问扁鹊的注释_《魏文王问扁鹊》及翻译
  19. 杭州市建筑工程师职称评审申报指南
  20. web test LoadRunner error list / error log

热门文章

  1. CodeForces - 1334D Minimum Euler Cycle(构造+模拟)
  2. DenyHosts教程:防暴力破解SSH密码
  3. hdu3549(网络流入门题-最大流的Ford-Fulkerson算法)
  4. Delphi之virtual,dynamic,abstract
  5. 漫游Kafka设计篇之性能优化
  6. 如何让你的大文件上传变得又稳又快?
  7. 高级数据结构与算法 | 二叉搜索树(Binary Search Tree)
  8. C++ 类和对象(二):构造函数、析构函数、拷贝构造函数、运算符重载
  9. kubernetes(六)k8s核心组件学习
  10. 经典|图解Linux内存性能优化核心思想