2025. 11. 22. 19:05ㆍCS & Algorithm/문제풀이
https://app.codility.com/c/run/trainingQ4R62N-U5Z/
Codility
Your browser is not supported Please, update your browser or switch to a different one. Learn more about what browsers are supported
app.codility.com

접근 방식
같은 값이 두 번 등장하면 짝이 맞으니까 사라지고, 홀수 번 등장하는 값만 마지막에 남기는 방식으로 풀이
List나 HashSet을 이용하여 해결!
- 배열을 왼쪽부터 오른쪽까지 순회하면서 원소를 하나씩 확인
- 어떤 값 x를 처음 만났을 때는 아직 짝이 없다는 의미이므로 저장
- 같은 값 x를 두 번째로 만나면 짝이 맞았다는 의미이므로 저장했던 것을 제거
이렇게 계속 반복하면,
짝이 두 번, 네 번, 여섯 번… 등장한 값은 모두 사라지고, 홀수 번(보통 1번) 등장한 값만 마지막에 남게 됨
나의 풀이 코드
내 풀이의 문제점
- list.contains(value) → 리스트 전체를 훑어야 하므로 O(N)
- list.remove(Integer.valueOf(value)) → 위치 찾기 + 뒤 요소 밀어주기까지 O(N)
이 연산들이 배열 길이 N번 반복되기 때문에 전체 시간 복잡도는 O(N²) 가 된다.
public int solution(int[] A) {
List<Integer> list = new ArrayList<>();
for (int i = 0; i < A.length; i++) {
int value = A[i];
if (list.contains(value)) {
list.remove(Integer.valueOf(value));
} else {
list.add(value);
}
}
return (list.size() > 0) ? list.get(0) : 0;
}
HashSet을 사용한 리팩토링 코드
List → HashSet으로 바꾸면서 contains, add, remove가 평균 O(1) 이 되어 전체 시간 복잡도가 O(N) 으로 내려감
import java.util.HashSet;
import java.util.Set;
class Solution {
public int solution(int[] A) {
Set<Integer> set = new HashSet<>();
for (int v : A) {
if (set.contains(v)) {
// 이미 한 번 등장했던 숫자 → 짝이 생겼으니 제거
set.remove(v);
} else {
// 처음 등장한 숫자 → 나중에 짝이 나올 수 있으니 추가
set.add(v);
}
}
// 문제 조건상 짝이 없는 원소는 정확히 하나 존재
// 따라서 set에는 그 숫자 하나만 남게 된다.
return set.iterator().next();
}
}
List와 Set 성능 비교
| 연산 | ArrayList | HashSet | 이유 |
| contains(value) | ❌ O(N) | ✔ O(1) | List는 전체 탐색, Set은 해시로 바로 찾음 |
| remove(value) | ❌ O(N) | ✔ O(1) | List는 찾고, 뒤 요소들까지 당겨야 함 |
| add(value) | ✔ O(1) amortized | ✔ O(1) | 거의 동일하지만 remove, contains에서 차이 극대화 |
👎 List(ArrayList)의 문제점 — O(N)
contains(value) = O(N)
List는 내부 구조가 순차 배열로 이루어져 있기 때문에 값이 있는지 확인하려면 처음부터 끝까지 하나씩 비교해야 한다.
: 최악의 경우 N번 비교 → O(N)
list.contains(x)
→ list[0] == x ?
→ list[1] == x ?
→ list[2] == x ?
…
→ list[N-1] == x ?
remove(value) = O(N)
remove(value) 실행 단계
- 값을 찾기 위해 전체 탐색 → O(N)
- 찾은 뒤 뒤 요소들을 한 칸씩 당김 → O(N)
remove ≒ O(N) + O(N) = O(N)
👍 Set(HashSet)의 강점
HashSet은 내부 구조가 해시 테이블루 구성
- 값 → hashCode()로 버킷 위치가 바로 계산됨
- 전체를 뒤지지 않고 해당 위치만 확인
- contains(value) = O(1)
- add(value) = O(1)
- remove(value) = O(1)
- O(N) × O(1) = O(N)
정리
List → 값 찾으려면 전체를 순회해야 한다 (선형 구조)
Set → 값의 위치를 해시로 바로 계산한다 (해시 테이블)
'CS & Algorithm > 문제풀이' 카테고리의 다른 글
| [Codility] CyclicRotation (0) | 2025.11.22 |
|---|---|
| [프로그래머스] 68644. 두 개 뽑아서 더하기 (0) | 2025.11.20 |
| [프로그래머스] 42748. K번째수 (0) | 2025.11.20 |
| [Codility] BinaryGap (0) | 2025.11.20 |
| [Leet Code] 20. Valid Parentheses (0) | 2025.11.20 |