代码随想录算法训练营第六天(1)|454.四数相加II

55 阅读2分钟

题目描述

给你四个整数数组 nums1nums2nums3 和 nums4 ,数组长度都是 n ,请你计算有多少个元组 (i, j, k, l) 能满足:

  • 0 <= i, j, k, l < n
  • nums1[i] + nums2[j] + nums3[k] + nums4[l] == 0

代码示例

from typing import List

class Solution:
    def fourSumCount(self, nums1: List[int], nums2: List[int], nums3: List[int], nums4: List[int]) -> int:
        # 使用字典记录 nums1 和 nums2 中数字的和及其出现的次数
        record = dict()
        
        # 遍历 nums1 和 nums2,记录和及其出现次数
        for i in range(len(nums1)):
            for j in range(len(nums2)):
                current_sum = nums1[i] + nums2[j]
                if current_sum not in record:
                    record[current_sum] = 1
                else:
                    record[current_sum] += 1
        
        result = 0  # 存储满足条件的组合数量
        
        # 遍历 nums3 和 nums4,查找和的相反数是否在 record 中,若在则累加次数
        for i in range(len(nums3)):
            for j in range(len(nums4)): 
                current_sum = nums3[i] + nums4[j]
                if -current_sum in record:
                    result += record[-current_sum]
        
        return result

第一眼看到这个问题时,我考虑使用四个循环逐个遍历可能的组合,但我意识到这样可能会漏掉一些组合。

在阅读完代码随想录之后,我学到了一种更为高效的解决方案。首先,我定义了一个 unordered_map(无序映射),其中的键存放 a 和 b 两数之和,值存放 a 和 b 两数之和出现的次数。然后,我遍历大 A 和大 B 数组,统计两个数组元素之和以及和出现的次数,并将它们放入映射中。接下来,我定义了一个整数变量 count,用来统计满足 a + b + c + d = 0 出现的次数。在遍历大 C 和大 D 数组时,我找到了如果 0 - (c + d) 在映射中出现过,就用 count 统计映射中对应的值,即出现的次数。最终,我返回了统计值 count。

这种方法通过巧妙地利用映射,避免了四个循环的低效遍历,提高了算法的效率。这次学习经历让我更深刻地理解了数据结构的应用,也拓展了我解决问题的思路。