刷题#将这个数字分组求偶数和|豆包Marscode Al 刷题

63 阅读4分钟

题目解析

这道题目要求从一组数字中选取每组中的一个数字组成一个新的数,目标是使得这个新数的各位数字之和为偶数。我们需要计算有多少种选择方法能达到这一目标。

思路

  1. 理解问题要求:

    • 你需要从每个数字组中选择一个数字,组成一个新的数字。
    • 目标是使得新数字的各位和为偶数。
  2. 关键点分析:

    • 新数字的各位数字之和是偶数,意味着所有选择的数字的和是偶数。
    • 数字的奇偶性是关键。你不需要关心每个数字的具体值,只关心它是奇数还是偶数。
  3. 奇偶性分析:

    • 只有偶数加偶数才是偶数,只有奇数加奇数才是偶数,偶数加奇数是奇数。
    • 因此,我们只需要知道每个数字组中有多少个偶数和奇数。
  4. 递归或动态规划思路:

    • 对于每一组数字,我们要决定从中选择一个偶数还是一个奇数。
    • 如果选择偶数,则不改变总和的奇偶性;选择奇数时,则会改变总和的奇偶性(偶变奇,奇变偶)。
  5. 最终的目标:

    • 计算出有多少种选法能使得最终组成的数字的和是偶数。

代码实现

pythonCopy Code
def countEvenSumNumbers(numbers):
    # 记录当前偶数和奇数的选择情况
    even_count = 1  # 当前偶数和偶数和为偶数的选法数
    odd_count = 0   # 当前奇数和偶数和为奇数的选法数
    
    # 遍历每个数字组
    for group in numbers:
        # 统计当前数字组中偶数和奇数的数量
        even_group = sum(1 for digit in group if int(digit) % 2 == 0)
        odd_group = len(group) - even_group
        
        # 新的选法数 = (偶数 + 偶数情况, 奇数 + 奇数情况)
        new_even_count = even_count * even_group + odd_count * odd_group
        new_odd_count = even_count * odd_group + odd_count * even_group
        
        # 更新选法数
        even_count, odd_count = new_even_count, new_odd_count
    
    return even_count

# 测试样例
print(countEvenSumNumbers(["123", "456", "789"]))  # 输出: 14
print(countEvenSumNumbers(["123456789"]))  # 输出: 4
print(countEvenSumNumbers(["14329", "7568"]))  # 输出: 10

代码解析

  1. 初始设定:

    • even_count = 1:初始时,选法数只有一种,即没有选择任何数字时的偶数和(即0)。
    • odd_count = 0:初始时,奇数和的选法数为0。
  2. 遍历每个数字组:

    • 对于每个数字组(例如 "123"、"456"),我们计算其中偶数和奇数的数量。
    • 然后,根据偶数和奇数的数量,更新当前偶数和奇数和的选法数。
  3. 更新选法数:

    • new_even_count:新的偶数和选法数,通过从偶数组和奇数组中选择数字后更新。
    • new_odd_count:新的奇数和选法数,通过从偶数组和奇数组中选择数字后更新。
  4. 返回结果:

    • 最终返回的 even_count 即为满足条件的选法数,即新数的各位和为偶数的选择方法数。

时间复杂度

  • 假设 numbers 的长度为 n,每个数字组的最大长度为 m
  • 对于每个数字组,我们需要遍历它的每个字符来判断奇偶性,这需要 O(m) 时间。
  • 总的时间复杂度为 O(n * m)

知识总结

  1. 奇偶性运算:

    • 在这道题目中,奇偶性是核心。通过只考虑每组数字的奇偶性,我们将问题从一个复杂的全排列问题简化为一个动态规划问题。
  2. 动态规划思想:

    • 我们在遍历每组数字时,利用前一步的结果更新当前的选法数。这种递推方式非常适合解决此类问题。
  3. 优化思路:

    • 通过把数字的奇偶性作为关键,避免了对每个数字的实际值进行复杂操作,减少了计算的复杂度。

学习心得

通过这道题的学习,我对动态规划的理解有了进一步加深。虽然这道题看似简单,但它强调了如何通过状态转移来高效地解决问题。尤其是在计算选法时,我们只关心结果的奇偶性,而不是每个数字的具体值,避免了复杂度的提升。


学习计划

  1. 基础题目:

    • 继续刷一些基础的动态规划和递归题目,如背包问题、子序列问题等,掌握如何使用状态转移方程来解决问题。
  2. 算法与数据结构:

    • 深入学习和实践常见的数据结构(如哈希表、堆、图等)以及算法(如贪心、分治、回溯等),提高解题思维和编程技巧。
  3. 错题本:

    • 记录所有遇到的难题和错误,定期回顾和复习,理解错误的原因并总结经验。

工具运用

结合AI刷题工具如豆包MarsCode AI平台,不仅可以快速获得题目的解法,还可以通过社区讨论和题解交流,提升对算法的理解和应用。通过错题回顾和总结,帮助自己不断优化代码和解题思路。