Category |
Difficulty |
Likes |
Dislikes |
algorithms |
Hard (62.04%) |
366 |
- |
Tags
dynamic-programming
| depth-first-search
Companies
Unknown
给出一些不同颜色的盒子 boxes
,盒子的颜色由不同的正数表示。
你将经过若干轮操作去去掉盒子,直到所有的盒子都去掉为止。每一轮你可以移除具有相同颜色的连续 k
个盒子(k >= 1
),这样一轮之后你将得到 k * k
个积分。
返回 你能获得的最大积分和 。
示例 1:
1 2 3 4 5 6 7 8
| 输入:boxes = [1,3,2,2,2,3,4,3,1] 输出:23 解释: [1, 3, 2, 2, 2, 3, 4, 3, 1] ----> [1, 3, 3, 4, 3, 1] (3*3=9 分) ----> [1, 3, 3, 3, 1] (1*1=1 分) ----> [1, 1] (3*3=9 分) ----> [] (2*2=4 分)
|
示例 2:
示例 3:
动态规划 + 递归(c++)
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
| /* * @lc app=leetcode.cn id=546 lang=cpp * * [546] 移除盒子 */
/** * f[l, r, k] = max(f[l, r-1, 0] + (k + 1)²) * * 6365676686 * f[0,0,0] = */
// @lc code=start class Solution { public: int f[100][100][100]; int removeBoxes(vector<int>& boxes) { memset(f, 0, sizeof f); return calculatePoints(boxes, 0, boxes.size() - 1, 0); } int calculatePoints(vector<int>& boxes, int l, int r, int k) { if (l > r) { return 0; } if (f[l][r][k] == 0) { int k1 = k, r1 = r; while (r1 > l && boxes[r1] == boxes[r1 - 1]) { --r1; ++k1; } f[l][r][k] = calculatePoints(boxes, l, r1 - 1, 0) + (k1 + 1) * (k1 + 1); for (int i = l; i < r1; ++i) { if (boxes[i] == boxes[r]) { f[l][r][k] = max(f[l][r][k], calculatePoints(boxes, l, i, k1 + 1) + calculatePoints(boxes, i + 1, r1 - 1, 0)); } } } return f[l][r][k]; } }; // @lc code=end
|