Cheapest Total Cost to Hire k Workers
Problem
You're hiring k workers from a row of candidates. In each session you may hire only from a window of size candidates at the front and back of the still-unhired row. Always hire the cheapest available worker (ties broken by lower index). Use two min-heaps — one for the front window, one for the back — and two pointers that converge.
Input
costs = [17,12,10,2,7,2,11,20,8], k = 3, candidates = 4Output
11Hire 2, then 2, then 7 from the rolling windows.
import heapq
def total_cost(costs, k, m):
l, r = 0, len(costs) - 1
left, right = [], []
while len(left) < m and l <= r:
heapq.heappush(left, costs[l]); l += 1
while len(right) < m and l <= r:
heapq.heappush(right, costs[r]); r -= 1
total = 0
for _ in range(k):
if not right or (left and left[0] <= right[0]):
total += heapq.heappop(left)
if l <= r: heapq.heappush(left, costs[l]); l += 1
else:
total += heapq.heappop(right)
if l <= r: heapq.heappush(right, costs[r]); r -= 1
return total
function totalCost(costs, k, m) {
let l = 0, r = costs.length - 1;
const left = [], right = [];
while (left.length < m && l <= r) { left.push(costs[l++]); }
while (right.length < m && l <= r) { right.push(costs[r--]); }
left.sort((a, b) => a - b); right.sort((a, b) => a - b);
let total = 0;
for (let i = 0; i < k; i++) {
if (right.length === 0 || (left.length && left[0] <= right[0])) {
total += left.shift();
if (l <= r) { left.push(costs[l++]); left.sort((a, b) => a - b); }
} else {
total += right.shift();
if (l <= r) { right.push(costs[r--]); right.sort((a, b) => a - b); }
}
}
return total;
}
class Solution {
public long totalCost(int[] costs, int k, int m) {
int l = 0, r = costs.length - 1;
PriorityQueue<Integer> left = new PriorityQueue<>(), right = new PriorityQueue<>();
while (left.size() < m && l <= r) left.offer(costs[l++]);
while (right.size() < m && l <= r) right.offer(costs[r--]);
long total = 0;
for (int i = 0; i < k; i++) {
if (right.isEmpty() || (!left.isEmpty() && left.peek() <= right.peek())) {
total += left.poll();
if (l <= r) left.offer(costs[l++]);
} else {
total += right.poll();
if (l <= r) right.offer(costs[r--]);
}
}
return total;
}
}
long long totalCost(vector<int>& costs, int k, int m) {
int l = 0, r = (int)costs.size() - 1;
priority_queue<int, vector<int>, greater<int>> left, right;
while ((int)left.size() < m && l <= r) left.push(costs[l++]);
while ((int)right.size() < m && l <= r) right.push(costs[r--]);
long long total = 0;
for (int i = 0; i < k; i++) {
if (right.empty() || (!left.empty() && left.top() <= right.top())) {
total += left.top(); left.pop();
if (l <= r) left.push(costs[l++]);
} else {
total += right.top(); right.pop();
if (l <= r) right.push(costs[r--]);
}
}
return total;
}