|
1 | 1 | package g3401_3500.s3500_minimum_cost_to_divide_array_into_subarrays
|
2 | 2 |
|
3 |
| -// #Hard #2025_03_30_Time_200_ms_(100.00%)_Space_88.62_MB_(_%) |
| 3 | +// #Hard #Array #Dynamic_Programming #Prefix_Sum |
| 4 | +// #2025_04_01_Time_28_ms_(92.31%)_Space_49.69_MB_(69.23%) |
4 | 5 |
|
5 | 6 | class Solution {
|
6 | 7 | fun minimumCost(nums: IntArray, cost: IntArray, k: Int): Long {
|
7 | 8 | val n = nums.size
|
8 |
| - val prefixNums = LongArray(n) |
9 |
| - var total: Long = 0 |
10 |
| - for (i in 0..<n) { |
11 |
| - total += nums[i].toLong() |
12 |
| - prefixNums[i] = total |
| 9 | + val k = k.toLong() |
| 10 | + val preNums = LongArray(n + 1) |
| 11 | + val preCost = LongArray(n + 1) |
| 12 | + for (i in 0..n - 1) { |
| 13 | + preNums[i + 1] = preNums[i] + nums[i] |
| 14 | + preCost[i + 1] = preCost[i] + cost[i] |
13 | 15 | }
|
14 |
| - val prefixCost = LongArray(n + 1) |
15 |
| - total = 0 |
16 |
| - for (i in 0..<n) { |
17 |
| - total += cost[i].toLong() |
18 |
| - prefixCost[i + 1] = total |
| 16 | + val dp = LongArray(n + 1) { |
| 17 | + Long.MAX_VALUE / 2 |
| 18 | + }.also { it[0] = 0L } |
| 19 | + for (r in 1..n) for (l in 0..r - 1) { |
| 20 | + val sumNums = preNums[r] * (preCost[r] - preCost[l]) |
| 21 | + val sumCost = k * (preCost[n] - preCost[l]) |
| 22 | + dp[r] = minOf(dp[r], dp[l] + sumNums + sumCost) |
19 | 23 | }
|
20 |
| - val memo: Array<LongArray> = Array<LongArray>(n) { LongArray(n + 1) } |
21 |
| - for (row in memo) { |
22 |
| - row.fill(-1) |
23 |
| - } |
24 |
| - val bestSplit = IntArray(n) |
25 |
| - bestSplit.fill(-1) |
26 |
| - return rec(0, 1, nums, prefixNums, prefixCost, k, memo, bestSplit) |
27 |
| - } |
28 |
| - |
29 |
| - private fun rec( |
30 |
| - index: Int, |
31 |
| - i: Int, |
32 |
| - nums: IntArray, |
33 |
| - prefixNums: LongArray, |
34 |
| - prefixCost: LongArray, |
35 |
| - k: Int, |
36 |
| - memo: Array<LongArray>, |
37 |
| - bestSplit: IntArray, |
38 |
| - ): Long { |
39 |
| - val n = nums.size |
40 |
| - if (index == n) { |
41 |
| - return 0 |
42 |
| - } |
43 |
| - if (memo[index][i] != -1L) { |
44 |
| - return memo[index][i] |
45 |
| - } |
46 |
| - if (bestSplit[index] != -1) { |
47 |
| - val j = bestSplit[index] |
48 |
| - val `val` = |
49 |
| - ( |
50 |
| - (prefixNums[j] + k.toLong() * i) * (prefixCost[j + 1] - prefixCost[index]) + |
51 |
| - rec(j + 1, i + 1, nums, prefixNums, prefixCost, k, memo, bestSplit) |
52 |
| - ) |
53 |
| - memo[index][i] = `val` |
54 |
| - return `val` |
55 |
| - } |
56 |
| - var best = Long.Companion.MAX_VALUE |
57 |
| - var bestIndex = -1 |
58 |
| - for (j in index..<n) { |
59 |
| - val `val` = |
60 |
| - ( |
61 |
| - (prefixNums[j] + k.toLong() * i) * (prefixCost[j + 1] - prefixCost[index]) + |
62 |
| - rec(j + 1, i + 1, nums, prefixNums, prefixCost, k, memo, bestSplit) |
63 |
| - ) |
64 |
| - if (`val` < best) { |
65 |
| - best = `val` |
66 |
| - bestIndex = j |
67 |
| - } |
68 |
| - } |
69 |
| - bestSplit[index] = bestIndex |
70 |
| - memo[index][i] = best |
71 |
| - return best |
| 24 | + return dp[n] |
72 | 25 | }
|
73 | 26 | }
|
0 commit comments