There are `N` workers.  The `i`-th worker has a `quality[i]` and a minimum wage expectation `wage[i]`.

Now we want to hire exactly K workers to form a paid group.  When hiring a group of K workers, we must pay them according to the following rules:

  1. Every worker in the paid group should be paid in the ratio of their quality compared to other workers in the paid group.
  2. Every worker in the paid group must be paid at least their minimum wage expectation.

Return the least amount of money needed to form a paid group satisfying the above conditions.

Example 1:

Input: quality = [10,20,5], wage = [70,50,30], K = 2
Output: 105.00000
Explanation: We pay 70 to 0-th worker and 35 to 2-th worker.

Example 2:

Input: quality = [3,1,10,10,1], wage = [4,8,2,2,7], K = 3
Output: 30.66667
Explanation: We pay 4 to 0-th worker, 13.33333 to 2-th and 3-th workers seperately.

Note:

  1. 1 <= K <= N <= 10000, where N = quality.length = wage.length
  2. 1 <= quality[i] <= 10000
  3. 1 <= wage[i] <= 10000
  4. Answers within 10^-5 of the correct answer will be considered correct.

这道题说是有N个员工,每个员工有个能力值,还有个薪水期望值,现在我们需要从中雇佣K个员工,需要满足两个条件:1. 每个员工的薪水要和其能力值成恒定比例。2. 每个员工的薪水不低于其期望值。让求雇佣满足要求的K个员工的最小花费是多少,博主最开始看到这题时,以为是背包问题,又看了一下是 Hard 的难度,更加坚定了是个 DP 问题。但实际上这却是一道贪婪算法能解决的问题,类型标签给的是堆 Heap,嗯,因缺斯汀。我们仔细来分析分析题目中限定必须满足的两个条件,先来看第一个,说是每个员工的薪水要和其能力值成恒定比例,意思是说假如两个员工A和B,若A的能力值是B的2倍,那么A的薪水就要是B的两倍,要雇佣的K个员工所有人的薪水和能力都是要成比例的,而这个比例一定是个恒定值,只要能够算出这个最低的薪水能力比例值,乘以K个员工的总能力值,就可以得到最少的总花费。第二个需要满足的条件是每个员工的薪水不能低于其期望值,则每个员工都有一个自己固定的薪水能力比例值,而需要求的那个最低的薪水能力比例值不能小于任何一个员工自己的比例值。当员工能力值越低,期望薪水越高的时候,其薪水能力比例值就越大,所以可以根据薪水能力比例值从大到小来排列员工。可以将员工的薪水能力比例值和其能力值组成 pair 对儿放到一个数组中,然后对这个数组进行排序,则默认就是对薪水能力比例值进行从小到大的排列。接下来的操作就跟之前那道 [Top K Frequent Words](http://www.cnblogs.com/grandyang/p/7689927.html) 非常像了,这里用一个最大堆,还要用一个变量 qsum 来累加员工的能力值,先将薪水能力比例最低的员工的能力值加到 qsum 中,同时加入到最大堆中,若堆中员工总数大于K了,则将堆顶能力值最大的员工移除,因为能力值越大意味着需要付的薪水越多。若堆中员工总数等于K了,则用当前员工的薪水能力比例乘以总的能力值数得到一个总花费,用来更新结果 res。为啥这样是正确的呢?因为当前员工的薪水能力比例值是大于堆中其他所有员工的,那么乘以恒定的总能力值,得出的总薪水数一定大于等于使用其他员工的薪水能力比例值,则每个员工可得到的薪水一定是大于等于其期望值的,这样就同时满足了两个条件,所以是符合题意的,最终更新完得到的总花费一定是最低的,参见代码如下:

class Solution {
public:
double mincostToHireWorkers(vector<int>& quality, vector<int>& wage, int K) {
double res = DBL_MAX, qsum = 0, n = quality.size();
vector<pair<double, int>> workers;
priority_queue<int> pq;
for (int i = 0; i < n; ++i) {
workers.push_back({double(wage[i]) / quality[i], quality[i]});
}
sort(workers.begin(), workers.end());
for (auto worker : workers) {
qsum += worker.second;
pq.push(worker.second);
if (pq.size() > K) {
qsum -= pq.top(); pq.pop();
}
if (pq.size() == K) {
res = min(res, qsum * worker.first);
}
}
return res;
}
};

Github 同步地址:

https://github.com/grandyang/leetcode/issues/857

类似题目:

Top K Frequent Words

参考资料:

https://leetcode.com/problems/minimum-cost-to-hire-k-workers/

https://leetcode.com/problems/minimum-cost-to-hire-k-workers/discuss/185085/75ms-Java-with-Explanations

https://leetcode.com/problems/minimum-cost-to-hire-k-workers/discuss/141768/Detailed-explanation-O(NlogN)

[LeetCode All in One 题目讲解汇总(持续更新中...)](https://www.cnblogs.com/grandyang/p/4606334.html)

[LeetCode] 857. Minimum Cost to Hire K Workers 雇佣K名工人的最低成本的更多相关文章

  1. [LeetCode] 857. Minimum Cost to Hire K Workers 雇K个工人的最小花费

    There are N workers.  The i-th worker has a quality[i] and a minimum wage expectation wage[i]. Now w ...

  2. 【LeetCode】857. Minimum Cost to Hire K Workers 解题报告(Python)

    作者: 负雪明烛 id: fuxuemingzhu 个人博客: http://fuxuemingzhu.cn/ 题目地址: https://leetcode.com/problems/minimum- ...

  3. 857. Minimum Cost to Hire K Workers

    There are N workers.  The i-th worker has a quality[i] and a minimum wage expectation wage[i]. Now w ...

  4. [Swift]LeetCode857. 雇佣 K 名工人的最低成本 | Minimum Cost to Hire K Workers

    There are N workers.  The i-th worker has a quality[i] and a minimum wage expectation wage[i]. Now w ...

  5. 贪心-谷歌-857. 雇佣 K 名工人的最低成本

    2020-03-15 22:00:39 问题描述: 有 N 名工人. 第 i 名工人的工作质量为 quality[i] ,其最低期望工资为 wage[i] . 现在我们想雇佣 K 名工人组成一个工资组 ...

  6. leetcode_雇佣 K 名工人的最低成本(优先级队列,堆排序)

    题干: 有 N 名工人. 第 i 名工人的工作质量为 quality[i] ,其最低期望工资为 wage[i] . 现在我们想雇佣 K 名工人组成一个工资组.在雇佣 一组 K 名工人时,我们必须按照下 ...

  7. LeetCode 1000. Minimum Cost to Merge Stones

    原题链接在这里:https://leetcode.com/problems/minimum-cost-to-merge-stones/ 题目: There are N piles of stones ...

  8. LeetCode 1130. Minimum Cost Tree From Leaf Values

    原题链接在这里:https://leetcode.com/problems/minimum-cost-tree-from-leaf-values/ 题目: Given an array arr of ...

  9. LeetCode 983. Minimum Cost For Tickets

    原题链接在这里:https://leetcode.com/problems/minimum-cost-for-tickets/ 题目: In a country popular for train t ...

随机推荐

  1. mysql 实现经纬度排序查找功能

    需求如下: 商品有多个门店,用户使用App时需要查找附近门店的商品,商品要进行去重分页. 思路: 1.确认mysql自带经纬度查询函数可以使用. 2.该需求需要利用分组排序,取每个商品最近门店的商品i ...

  2. Vue.js 源码分析(十八) 指令篇 v-for 指令详解

    我们可以用 v-for 指令基于一个数组or对象来渲染一个列表,有五种使用方法,如下: <!DOCTYPE html> <html lang="en"> & ...

  3. 【UOJ#76】【UR #6】懒癌(动态规划)

    [UOJ#76][UR #6]懒癌(动态规划) 题面 UOJ 题解 神....神仙题. 先考虑如果是完全图怎么做... 因为是完全图,所以是对称的,所以我们只考虑一个有懒癌的人的心路历程. 如果只有一 ...

  4. Java开发在线考试系统 使用ssh框架编写源码

    开发工具: Eclipse,  Tomcat,  MySql       1.  登录页面登录功能, 输入用户名与密码, 选择角色, 滑动箭头拉到最右边才可以点击登录       2.  学生角色登录 ...

  5. 命令 docker rm | docker rmi | docker prune 的差异

    区别: docker rm : 删除一个或多个 容器 docker rmi : 删除一个或多个 镜像 docker prune : 用来删除不再使用的 docker 对象 一.docker rm 命令 ...

  6. Flutter 安装笔记

    一. 安装镜像(有vpn的不用理) 1  打开终端 输入 open ~  ,回车 2  双击 .bash_profile  3  添加以下代码 后保存关闭即可(代码可能会变请直接到https://fl ...

  7. shuffle调优

    目录 一.概述 二.shuffle的定义 三.ShuffleMananger发展概述 四.HashShuffleManager的运行原理 4.1 未经优化的HashShuffleManager 4.2 ...

  8. 从html富文本中提取纯文本

    其实从html富文本中提取纯文本很简单,富文本基本上是使用html标签给文本加上丰富多彩的样式. 所以只需要将富文本字符串中的“<.....>”标签剔除,即可得到纯文本.我们可以使用正则表 ...

  9. 白话SCRUM之五:四种会议

    在SCRUM方法中定义了4种会议活动: Sprint planning Daily meeting Sprint review Sprint retrospective 除去开发活动外这4种会议构成了 ...

  10. Linux Kernel PANIC(三)--Soft Panic/Oops调试及实例分析【转】

    转自:https://blog.csdn.net/gatieme/article/details/73715860 版权声明:本文为博主原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原 ...