算法: 数组是否可以分成和相等的两个子集416. Partition Equal Subset Sum

Posted AI架构师易筋

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了算法: 数组是否可以分成和相等的两个子集416. Partition Equal Subset Sum相关的知识,希望对你有一定的参考价值。

416. Partition Equal Subset Sum

Given a non-empty array nums containing only positive integers, find if the array can be partitioned into two subsets such that the sum of elements in both subsets is equal.

Example 1:

Input: nums = [1,5,11,5]
Output: true
Explanation: The array can be partitioned as [1, 5, 5] and [11].

Example 2:

Input: nums = [1,2,3,5]
Output: false
Explanation: The array cannot be partitioned into equal sum subsets.

Constraints:

  • 1 <= nums.length <= 200
  • 1 <= nums[i] <= 100

动态规划 - 制表

我们可以将 dp 方法转换为迭代版本。这里我们将再次使用dp数组,其中dp[sum]将表示是否sum可以实现。最初,我们dp[0] = true总是可以实现 0 和。然后对于每个元素num,我们将迭代并查找是否可以j通过添加num一些先前可形成的总和来形成总和。

需要注意的一点是,必须在下面的内部循环中从右到左进行迭代,以避免将多个总和标记j1为可实现,然后再次使用该结果将另一个更大的总和j2( j2=j1+num) 标记为可实现。这是错误的,因为这意味着选择num多次。所以我们从右到左开始,避免覆盖之前在当前循环中更新的结果。

以例子[1,5, 5,11] 推算,因为遇到11刚好是和的一半,所以放在最后。

  1. dp[1] = dp[0] true
  2. dp[6] = dp[1] true
  3. dp[11] = dp[6] true 得到结果
class Solution:
    def canPartition(self, nums: List[int]) -> bool:
        total_sum = sum(nums)
        if total_sum & 1: return False
        half_sum = total_sum // 2
        dp = [True] + [False]*half_sum
        for num in nums:
            for j in range(half_sum, num-1, -1):
                dp[j] |= dp[j-num]
            if dp[half_sum]:
                return True
        return dp[half_sum]
        

参考

https://leetcode.com/problems/partition-equal-subset-sum/discuss/1624939/C%2B%2BPython-5-Simple-Solutions-w-Explanation-or-Optimization-from-Brute-Force-to-DP-to-Bitmask

以上是关于算法: 数组是否可以分成和相等的两个子集416. Partition Equal Subset Sum的主要内容,如果未能解决你的问题,请参考以下文章

416-分割等和子集(01背包)

[416]. 分割等和子集

416分割等和子集

算法每日一题

算法每日一题

题目地址(416. 分割等和子集)