Problem
두 배열에서 중복되는 원소들을 모아서 만든 배열을 구하는 문제입니다.
Solution
각 배열에 같은 숫자가 여러 개 존재하면 겹치는 만큼 전부 리턴해야 하기 때문에 일반적인 교집합과는 조금 다릅니다.
결국 각 숫자에 있는 값들을 전부 비교하는 수밖에 없습니다.
원소의 범위가 정해져 있지 않으므로 HashMap
을 사용해서 개수를 비교하면 됩니다.
Folllow up 1 에서 두 배열이 정렬된 상태면 어떻게 최적화 가능하냐는 질문이 있습니다.
각 배열이 정렬된 상태라면 Two pointer
를 사용하여 풀 수 있습니다.
Follow up 2 에서 정렬된 상태이면서 한쪽 배열의 크기가 무조건 작을 경우 어떻게 최적화 하는 지 다시 물어봅니다.
nums1
배열의 크기가 작다면 nums1
배열을 전체 순회하면서 각 원소 값을 nums2
에서 이진 탐색을 이용하여 찾으면 됩니다.
중복된 값 처리 때문에 귀찮아서 구현은 생략합니다.
Java Code
// Normal Solution - Using HashMap O(n + m)
class Solution {
public int[] intersect(int[] nums1, int[] nums2) {
Map<Integer, Integer> map = new HashMap<>(); // <number, count>
List<Integer> list = new ArrayList<>();
for (int num : nums1) {
map.merge(num, 1, Integer::sum);
}
for (int num : nums2) {
int count = map.getOrDefault(num, 0);
if (count > 0) {
list.add(num);
map.put(num, count - 1);
}
}
return list.stream().mapToInt(k -> k).toArray();
}
}
// Follow up 1 - O(max(n, m))
// What if the given array is already sorted?
// How would you optimize your algorithm?
// 두 배열이 정렬된 상태면 two-pointer 를 사용해서 최적화 가능
class Solution {
public int[] intersect(int[] nums1, int[] nums2) {
List<Integer> list = new ArrayList<>();
int i = 0, j = 0;
Arrays.sort(nums1);
Arrays.sort(nums2);
while (i < nums1.length && j < nums2.length) {
if (nums1[i] == nums2[j]) {
list.add(nums1[i]);
i++;
j++;
} else if (nums1[i] < nums2[j]) {
i++;
} else {
j++;
}
}
return list.stream().mapToInt(k -> k).toArray();
}
}
'알고리즘 문제 > LeetCode' 카테고리의 다른 글
[LeetCode Easy] Best Time to Buy and Sell Stock (Java) (0) | 2020.12.23 |
---|---|
[LeetCode Easy] Number of 1 Bits (Java, Kotlin) (0) | 2020.11.26 |
[LeetCode Easy] Missing Number (Java, Kotlin) (0) | 2020.11.26 |
[LeetCode Easy] Employee Importance (Java) (0) | 2020.11.25 |
[LeetCode Easy] Reshape the Matrix (Java) (0) | 2020.11.25 |