Watch 10 video solutions for Greatest Sum Divisible by Three, a medium level problem involving Array, Dynamic Programming, Greedy. This walkthrough by NeetCodeIO has 17,003 views views. Want to try solving it yourself? Practice on FleetCode or read the detailed text solution.
Given an integer array nums, return the maximum possible sum of elements of the array such that it is divisible by three.
Example 1:
Input: nums = [3,6,5,1,8] Output: 18 Explanation: Pick numbers 3, 6, 1 and 8 their sum is 18 (maximum sum divisible by 3).
Example 2:
Input: nums = [4] Output: 0 Explanation: Since 4 is not divisible by 3, do not pick any number.
Example 3:
Input: nums = [1,2,3,4,4] Output: 12 Explanation: Pick numbers 1, 3, 4 and 4 their sum is 12 (maximum sum divisible by 3).
Constraints:
1 <= nums.length <= 4 * 1041 <= nums[i] <= 104Problem Overview: You are given an integer array and need the maximum possible sum of elements such that the final sum is divisible by 3. You can choose any subset of elements. The challenge is maximizing the total while ensuring the remainder when divided by three equals zero.
Approach 1: Dynamic Programming with Modulo States (O(n) time, O(1) space)
This method tracks the best possible sums for each remainder when divided by three. Maintain a small DP array where dp[r] stores the maximum sum whose modulo with 3 equals r. For every number in the array, update the states by combining the current value with existing sums and adjusting the modulo using (oldRemainder + num) % 3. Only the largest sums for each remainder are kept. Since there are only three states (0, 1, 2), the memory footprint remains constant and updates are fast. This approach effectively builds the best divisible sum incrementally while scanning the array once.
Approach 2: Direct Modulo Adjustment (Greedy) (O(n) time, O(1) space)
Start by computing the total sum of all numbers. If the sum is already divisible by three, that value is the answer. Otherwise, remove the smallest elements necessary to fix the remainder. If the total remainder is 1, remove either one number with remainder 1 or two numbers with remainder 2. If the remainder is 2, remove either one number with remainder 2 or two numbers with remainder 1. Tracking the smallest candidates while iterating the array avoids sorting and keeps the solution linear. This approach uses a greedy observation about minimizing the removed sum to maximize the remaining divisible total.
The DP method is conceptually clean and aligns with problems involving remainder states, which commonly appear in dynamic programming. The greedy adjustment approach is slightly more intuitive once you recognize that only the modulo remainder matters.
Recommended for interviews: The dynamic programming solution is the safest explanation during interviews because it generalizes well to other remainder problems and demonstrates strong DP reasoning. The greedy modulo adjustment solution is equally optimal in O(n) time but relies on recognizing the mathematical property of divisibility by three. Showing the DP reasoning first and then mentioning the greedy optimization signals strong problem‑solving depth.
| Approach | Time | Space | When to Use |
|---|---|---|---|
| Dynamic Programming with Modulo States | O(n) | O(1) | General case when reasoning about remainders and subset sums |
| Direct Modulo Adjustment (Greedy) | O(n) | O(1) | When you recognize the remainder property and want a simpler implementation |