forked from neetcode-gh/leetcode
-
Notifications
You must be signed in to change notification settings - Fork 0
/
0621-task-scheduler.js
107 lines (83 loc) · 3 KB
/
0621-task-scheduler.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
/**
* https://leetcode.com/problems/task-scheduler/
* Time O(N * log(N)) | Space O(N)
* @param {character[]} tasks
* @param {number} n
* @return {number}
*/
var leastInterval = function(tasks, n) {
const frequencyMap = getFrequencyMap(tasks)
const maxHeap = getMaxHeap(frequencyMap)
return getMinimumCpuIntervals(maxHeap, n)
}
var getFrequencyMap = (tasks, frequencyMap = new Array(26).fill(0)) => {
for (const task of tasks) {
const index = task.charCodeAt(0) - 'A'.charCodeAt(0);
frequencyMap[index]++;
}
return frequencyMap;
}
const getMaxHeap = (frequencyMap, maxHeap = new MaxPriorityQueue()) => {
for (const frequency of frequencyMap) {
const hasFrequency = 0 < frequency;
if (hasFrequency) maxHeap.enqueue(frequency)
}
return maxHeap
}
const getMinimumCpuIntervals = (maxHeap, n, cpuIntervals = [ 0 ]) => {
while (!maxHeap.isEmpty()) {
const { iterations, coolingPeriodQueue } = execute(n, maxHeap, cpuIntervals)
reQueueCoolingPeriod(coolingPeriodQueue, maxHeap)
if (!maxHeap.isEmpty()) cpuIntervals[0] += iterations
}
return cpuIntervals[0]
}
const execute = (n, maxHeap, cpuIntervals, iterations = (n + 1), coolingPeriodQueue = new Queue()) => {
while ((0 < iterations) && !maxHeap.isEmpty()) {
const frequency = maxHeap.dequeue().element;
const hasFrequency = 0 < (frequency - 1);
if (hasFrequency) coolingPeriodQueue.enqueue(frequency - 1);
cpuIntervals[0]++;
iterations--;
}
return { iterations, coolingPeriodQueue };
}
const reQueueCoolingPeriod = (coolingPeriodQueue, maxHeap) => {
while (!coolingPeriodQueue.isEmpty()) {
maxHeap.enqueue(coolingPeriodQueue.dequeue())
}
}
/**
* https://leetcode.com/problems/task-scheduler/
* Time O(N) | Space O(1)
* @param {character[]} tasks
* @param {number} n
* @return {number}
*/
var leastInterval = function(tasks, n) {
const frequencyMap = getFrequencyMap(tasks);
const maxFrequency = getMaxFrequency(frequencyMap);
const mostFrequentTask = getMostFrequentTask(frequencyMap, maxFrequency);
const interval = ((maxFrequency - 1) * (n + 1)) + mostFrequentTask;
return Math.max(tasks.length, interval);
}
var getFrequencyMap = (tasks, frequencyMap = new Array(26).fill(0)) => {
for (const task of tasks) {
const index = task.charCodeAt(0) - 'A'.charCodeAt(0);
frequencyMap[index]++;
}
return frequencyMap;
}
const getMaxFrequency = (frequencyMap, maxFrequency = 0) => {
for (const frequency of frequencyMap) {
maxFrequency = Math.max(maxFrequency, frequency);
}
return maxFrequency;
}
const getMostFrequentTask = (frequencyMap, maxFrequency, mostFrequentTask = 0) => {
for (const frequency of frequencyMap) {
const isSame = frequency === maxFrequency;
if (isSame) mostFrequentTask++;
}
return mostFrequentTask;
}