-
Notifications
You must be signed in to change notification settings - Fork 229
/
Copy path1986-minimum-number-of-work-sessions-to-finish-the-tasks.js
95 lines (82 loc) · 2.18 KB
/
1986-minimum-number-of-work-sessions-to-finish-the-tasks.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
/**
* @param {number[]} tasks
* @param {number} sessionTime
* @return {number}
*/
const minSessions = function(tasks, sessionTime) {
const n = tasks.length
const limit = 1 << n
const dp = Array(limit).fill(Infinity)
dp[0] = 0
for(let mask = 1; mask < limit; mask++) {
for(let sub = mask; sub; sub = (sub - 1) & mask) {
if(valid(sub)) {
dp[mask] = Math.min(dp[mask], dp[mask - sub] + 1)
}
}
}
return dp[limit - 1]
function valid(sub) {
let sum = 0
for(let i = 0; i < 14; i++) {
if((sub >> i) & 1) sum += tasks[i]
}
return sum <= sessionTime
}
};
// another
/**
* @param {number[]} tasks
* @param {number} sessionTime
* @return {number}
*/
const minSessions = function(tasks, sessionTime) {
const n = tasks.length
const dp = Array.from({ length: 1 << 14 }, () => Array(16).fill(-1))
return fn(0, 0)
function fn(mask, consumed) {
if (mask === (1 << n) - 1) {
return consumed === 0 ? 0 : 1
}
if (dp[mask][consumed] !== -1) {
return dp[mask][consumed];
}
let result = Number.MAX_VALUE;
if (consumed > 0) {
result = Math.min(result, 1 + fn(mask, 0));
}
for (let i = 0; i < n; i++) {
if ((mask & (1 << i)) === 0 && consumed + tasks[i] <= sessionTime) {
result = Math.min(result, fn(mask | (1 << i), consumed + tasks[i]));
}
}
return dp[mask][consumed] = result;
}
};
// another
/**
* @param {number[]} tasks
* @param {number} sessionTime
* @return {number}
*/
function minSessions(tasks, sessionTime) {
const n = tasks.length
const memo = Array.from({ length: 1 << n }, () => Array(15))
return helper((1 << n) - 1, 0)
function helper(mask, remain) {
if(mask === 0) return 0
if(memo[mask][remain] != null) return memo[mask][remain]
let res = n
for(let i = 0; i < n; i++) {
if((1 << i) & mask) {
const newMask = mask & (~(1 << i))
if(tasks[i] <= remain) {
res = Math.min(res, helper(newMask, remain - tasks[i]))
} else {
res = Math.min(res, helper(newMask, sessionTime - tasks[i]) + 1)
}
}
}
return memo[mask][remain] = res
}
}