两个数组的交集 II

题目

给定两个数组,编写一个函数来计算它们的交集。

实例

示例 1:
输入: nums1 = [1,2,2,1], nums2 = [2,2]
输出: [2,2]

示例 2:
输入: nums1 = [4,9,5], nums2 = [9,4,9,8,4]
输出: [4,9]

解题

思路

方法一:

哈希表,把数组1的所有元素都放到哈希表中,并记录次数。然后再遍历数组2,看哈希表中是否有元素,有的话看次数是否在0以上,都满足的话就放入结果集,并把次数减1

时间复杂度为O(n) 空间复杂度为O(n)

方法二:

先把两个数组排序,然后定义两个指针分别指向两个数组的起点,比较两个指针下的元素大小,相同则放入结果集然后两个指针分别向后移动一位。第一个指针下的元素大于第二个下的元素的话,第二个指针后移一位,第一个指针下的元素小于第二个下的元素的话,第一个指针后移一位。

时间复杂度为O(nlogn) 空间复杂度为O(1)

ps 在数组规模很小的时候,方法二不一定比方法一耗时长。

代码

方法一

class Solution {
    public int[] intersect(int[] nums1, int[] nums2) {
        Map<Integer, Integer> map = new HashMap<>();
        for (int value : nums1) {
            if (map.containsKey(value)) {
                map.put(value, map.get(value) + 1);
            } else {
                map.put(value, 1);
            }
        }

        List<Integer> ansList = new ArrayList<>();
        for (int value : nums2) {
            if (map.containsKey(value) && map.get(value) > 0) {
                ansList.add(value);
                map.put(value, map.get(value) - 1);
            }
        }

        int[] ans = new int[ansList.size()];
        int idx = 0;
        for (Integer num : ansList) {
            ans[idx++] = num;
        }

        return ans;
    }
}

方法二

class Solution {
    public int[] intersect(int[] nums1, int[] nums2) {
        Arrays.sort(nums1);
        Arrays.sort(nums2);

        int idx1 = 0, idx2 = 0;

        List<Integer> ansList = new ArrayList<>(nums1.length);
        while (idx1 < nums1.length && idx2 < nums2.length) {
            int value1 = nums1[idx1], value2 = nums2[idx2];
            if (value1 == value2) {
                ansList.add(value1);
                idx1++;
                idx2++;
            } else if (value1 > value2) {
                idx2++;
            } else {
                idx1++;
            }
        }

        int[] ans = new int[ansList.size()];
        int idx = 0;
        for (Integer value : ansList) {
            ans[idx++] = value;
        }
        return ans;
    }
}