成人免费xxxxx在线视频软件_久久精品久久久_亚洲国产精品久久久_天天色天天色_亚洲人成一区_欧美一级欧美三级在线观看

【動態規劃】LeetCode 題解:416-分割等和子集

開發 前端
動態規劃,是有一定難度的算法題類型,也是面試大廠時比較常看到的題目,有掌握的必要性。

大家好,我是前端西瓜哥,有三個月沒做算法題了,這次就來做一道動態規劃中難度較低的題。

題目

給你一個只包含正整數的非空數組 nums。請你判斷是否可以將這個數組分割成兩個子集,使得兩個子集的元素和相等。

示例 1:

輸入:nums = [1,5,11,5]
輸出:true
解釋:數組可以分割成 [1, 5, 5] [11]

示例 2:

輸入:nums = [1,2,3,5]
輸出:false
解釋:數組不能分割成兩個元素和相等的子集。

題目來源:

https://leetcode.cn/problems/partition-equal-subset-sum。

題解

動態規劃,它的模型需要符合 多階段決策最優解模型,即要推導出最后的結果,它需要經歷多個階段。

比如經典的跳樓梯,假如你要跳到第 7 階梯的樓梯,你需要先知道跳到第 5 和第 6 階梯需要走的步數。

還比如 0-1 背包問題,我們在決策是否要放入第 n 個物品,我們需要知道上一個決策完成后,書包的所有可能的重量。

這些都是 階段。我們讓多個選擇同時并行發生,產生一個個階段,并記下狀態,給下一個狀態使用。

我們回到正題。

題目意思是問能否將數組拆分成兩個子數組,這兩個子數組的和相等。

其實這就等價于,數組元素中是否存在一個子數組,它的和為原數組的總和除以 2,這時它就變成了經典 0-1 背包問題,你需要決策每個階段是否放入特定的數組元素,直到剛好為總和除以 2。

0-1 背包問題,有在書包有最大承重情況下,求放入物體的最大重量。或是提升到二維,求放入物體的最大價值。

這道題屬于前者。

先看完整的題解:

function canPartition(nums) {
const sum = nums.reduce((sum, curr) => sum + curr, 0);
if (sum % 2 === 1) return false;
const half = sum / 2;
if (nums[0] === half) return true;
const dp = new Array(nums.length);
for (let i = 0; i < dp.length; i++) {
dp[i] = new Array(half + 1).fill(false);
}
dp[0][0] = true;
if (nums[0] <= half) {
dp[0][nums[0]] = true;
}
for (let i = 1; i < dp.length; i++) {

for (let j = 0; j < dp[i].length; j++) {
if (dp[i - 1][j] === true) {
dp[i][j] = true;
if (j + nums[i] < half) {
dp[i][j + nums[i]] = true;
} else if (j + nums[i] === half) {
return true;
}
}
}
}
return false;
};

這里的要點是構建一個二維布爾值數組 dp,用來保存每個階段的狀態,對于 dp[i][j],i 表示決策第 i 個元素是否被放入,j 表示子數組總和。

所以 dp[i][j] 的意思就是在決策第 i 個元素的階段,是否存在一種可能,讓總和為 j。

圖片

因為當前階段需要靠上一個階段推導,所以我們需要初始化第一階段的狀態:

const dp = new Array(nums.length);
for (let i = 0; i < dp.length; i++) {
dp[i] = new Array(half + 1).fill(false);
}
dp[0][0] = true;
if (nums[0] <= half) {
dp[0][nums[0]] = true;
}

然后推導下一個階段時,就遍歷上一階段的值,如果為 true,就基于它決策加入當前元素和不加入當前元素后得到的新的總和,在對應的位置標記為 true,直到和為目標值。

for (let i = 1; i < dp.length; i++) {
for (let j = 0; j < dp[i].length; j++) {
if (dp[i - 1][j] === true) {
dp[i][j] = true;
if (j + nums[i] < half) {
dp[i][j + nums[i]] = true;
} else if (j + nums[i] === half) {
return true;
}
}
}
}

其實還可以做內存優化,將二維數組轉換為一維數組,這需要用從后往前遍歷數組的技巧。

這里還用二維數組的解法,是因為它還是比較經典的,有普適性,適合用于講解。一些題目中,甚至能將優化為幾個變量,比如跳樓梯。

結尾

動態規劃,是有一定難度的算法題類型,也是面試大廠時比較常看到的題目,有掌握的必要性。

責任編輯:姜華 來源: 前端西瓜哥
相關推薦

2021-01-21 08:23:29

鏈表單鏈表循環鏈表

2021-03-12 08:19:20

數組跳躍游戲

2025-02-18 12:00:00

ROIPython計算機視覺

2021-03-02 08:21:58

LeetCode括號

2021-01-15 08:19:26

二維數組LeetCode

2023-01-06 08:42:41

動態規劃字符

2021-01-22 08:30:50

LeetCode數字數組

2021-02-04 08:18:53

LeetCode鏈表

2021-03-17 08:19:22

二叉樹LeetCode

2021-10-28 18:58:57

動態規劃數據結構算法

2022-12-29 08:12:51

動態規劃profit

2020-07-07 08:02:33

動態規劃緩存枚舉

2021-01-04 08:37:53

動態規劃DP

2011-08-03 13:25:19

布線系統規劃

2021-03-15 06:04:47

斐波那契數列背包問題算法

2021-03-22 08:23:29

LeetCode二叉樹節點

2021-01-28 08:20:41

鏈表空間復雜度

2021-10-08 11:13:41

子集問題數據結構算法

2021-09-29 11:30:03

子集問題模板題

2021-01-13 08:41:08

整數動態規劃
點贊
收藏

51CTO技術棧公眾號

主站蜘蛛池模板: 成人av一区| 91亚洲国产成人久久精品网站 | 日韩欧美一级精品久久 | 蜜月aⅴ免费一区二区三区 99re在线视频 | 免费一区 | 精品欧美一区二区三区久久久 | 免费观看av网站 | 熟女毛片 | 精品中文字幕一区二区三区 | 日韩一级黄色毛片 | 亚洲综合色 | 中文字幕一级毛片 | 欧美综合自拍 | 一区二区三区四区不卡视频 | 亚洲免费观看 | 国产一区二区日韩 | 天堂一区二区三区四区 | 国产成人高清成人av片在线看 | 成人欧美一区二区三区在线播放 | 欧美一二三 | 天天爽夜夜操 | 逼逼网 | 亚洲欧美一区二区三区在线 | 我想看一级黄色毛片 | 99热在线观看精品 | 精品在线视频播放 | 一级高清 | 奇米视频777| 国产亚洲欧美在线 | 中文在线亚洲 | 激情婷婷 | 中文字幕一区二区三区乱码在线 | 日韩图区 | 在线中文视频 | 欧美日韩一二三区 | 欧美影院 | 久久久久久综合 | 国产精品99久久久久久动医院 | 国产精品揄拍一区二区 | 欧美日韩在线一区二区三区 | 日本精品一区二区在线观看 |