ให้อาร์เรย์ nums ของจำนวนเต็ม ต้องการหาผลรวมสูงสุดของสมาชิกในอาร์เรย์ที่หารด้วย 3 ลงตัว ตัวอย่างเช่น อินพุต [3,6,5,1,8] ผลลัพธ์คือ 18 เพราะเลือกย่อยอาร์เรย์ [3,6,1,8] ได้ผลรวม 18 ซึ่งหารด้วย 3 ลงตัว
ขั้นตอนการแก้ปัญหา (Dynamic Programming)
n:= ขนาดของอาร์เรย์nums- สร้างตาราง DP ขนาด
(n + 1) x 3โดยdp[i][j]เก็บผลรวมสูงสุดจากiตัวแรกที่ modulo 3 ได้j - กำหนดค่าเริ่มต้น:
dp[0][0] = 0,dp[0][1] = -inf,dp[0][2] = -inf - วนลูป
iจาก 1 ถึงn:x := nums[i - 1]- คัดลอกค่าเดิม:
dp[i][j] := dp[i-1][j]สำหรับj = 0,1,2 - ลองนำ
xมารวม: สำหรับj = 0,1,2คำนวณk = (x + j) % 3แล้วอัปเดตdp[i][k] = max(dp[i][k], dp[i-1][j] + x)
- คืนค่า
dp[n][0]
ตัวอย่างโค้ด C++
#include <bits/stdc++.h>
using namespace std;
class Solution {
public:
int maxSumDivThree(vector<int>& nums) {
int n = nums.size();
vector<array<int, 3>> dp(n + 1);
dp[0] = {0, INT_MIN, INT_MIN};
for (int i = 1; i <= n; i++) {
int x = nums[i-1];
dp[i] = dp[i-1];
for (int j = 0; j < 3; j++) {
int k = (x + j) % 3;
dp[i][k] = max(dp[i][k], dp[i-1][j] + x);
}
}
return dp[n][0];
}
};
int main() {
vector<int> v = {3,6,5,1,8};
Solution ob;
cout << ob.maxSumDivThree(v);
}
Input
[3,6,5,1,8]
Output
18