力扣,698. 划分为k个相等的子集,递归+回溯,暴力出奇迹

  1. 划分为k个相等的子集
    https://leetcode-cn.com/problems/partition-to-k-equal-sum-subsets/
    在这里插入图片描述
    这题怎么说呢,看到那个len(nums)<16没,这就是叫我们使劲穷举的意思!!!!
    递归+回溯
    想法就是首先就是和不够k整除的,直接返回False,
    其次利用数组中求子集和为target的想法,整个代码也是它的模板的扩充。
    就按例题来分析,
    假设k=4,每组的值为5,我们从数组中找出一组数为5的,然后从原始的数组中去掉这组数,在找一组和为5的,然后在去掉这组数,一直到能找到4组数都为5的,就返回True,否则False。
    代码如下。
from collections import defaultdict
def canPartitionKSubsets(self, nums: List[int], k: int) -> bool:
    ssum = sum(nums)
    if ssum%k != 0:
        return False
    a = ssum//k   ##每组的和
    self.ans = False
    nums = sorted(nums,reverse = True)
    self.nums = defaultdict(int)
    for d in nums:
        self.nums[d] += 1 ####存储所有值
    self.used = defaultdict(int) ####存储用过的值,把用过的去掉。
    def rec(nums,c,a,s):####c是第几组,a是每一组的和,s当前组的目前值。
        if s>a: ##若当前值大于a,则返回
            return    
        if c == k and s == a: ####若c==k,且s=a,即最后一组也能凑到a,就直接返回真
            self.ans = True
            return             
        if self.ans: ####若果结果已经是真了,也就不用再递归乱跑了,直接出去吧。
            return 
        if s == a: #####如果当前组的当前值等于a,那么就到下一组。
            c += 1
            nums = []
            for h in self.nums: ####这里是用self.nums来存储所有值,self.used来存储已经用过的,把用过了去掉。
                nums += [h] *(self.nums[h] -self.used[h])
            print(self.used)                
            rec(nums,c,a,0)
            c-=1 ###恢复现场
        for i in range(len(nums)): ####求子集和为target
            s += nums[i]
            self.used[nums[i]] += 1
            rec(nums[i+1:],c,a,s)
            s -= nums[i]   ####恢复现场
            self.used[nums[i]] -= 1###恢复现场
    rec(nums,1,a,0)
    return self.ans
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值