728x90
반응형
문제 설명
해당 문제는 진열대에 나열된 보석들 중 모든 종류의 보석을 하나 이상 포함하는 가장 짧은 구간을 찾는 문제이다.
예를 들어 보석 종류가 4개라면 이 4가지 종류를 모두 포함하는 가장 짧은 구간의 시작과 끝 인덱스를 반환해야 한다.
핵심 방법
슬라이딩 윈도우 + 해시맵(map) 을 사용하여 현재 구간 내 보석의 종류를 세고,
모든 종류가 포함되었을 때 왼쪽 포인터를 줄이며 최소 구간을 갱신하는 방식이다.
슬라이딩 윈도우(Sliding Window) 기법은 배열이나 리스트에서 일정한 구간(윈도우)을 유지하며 왼쪽, 오른쪽 포인터를 이동시키는 방식으로 문제를 푸는 알고리즘 기법이다. Two Pointer 기법과 비슷하며 두 포인터의 구간을 검색하고 진행 방향이 같다는 것이 핵심이다.
Two Pointer 기법에 대한 자세한 내용은 아래 블로그에서 확인할 수 있다.
Two Pointer 기법
1차원 배열에서 각자 다른 원소를 가리키는 2개의 포인터를 사용하여 목표값을 구하기 위한 기법완전탐색 O(n^2)보다 효율적인 O(n)으로 동작정렬된 배열에서 효율적으로 동작한다. 왜?leftP는 가장
jinho082008.tistory.com
#include <string>
#include <vector>
#include <map>
#include <set>
#include <climits>
using namespace std;
vector<int> solution(vector<string> gems) {
map<string, int> m; // 현재 윈도우 내 보석 종류별 개수를 저장
vector<vector<int>> results; // 가능한 구간들을 저장
set<string> s;
for(string str : gems)
s.insert(str); // 보석 종류를 set으로 구분하여 전체 종류 수를 파악
int gemsCount = s.size(); // 전체 보석 종류 수
int start = 0; // 현재 슬라이딩 윈도우의 시작 인덱스
string frontGem = gems[0]; // 현재 윈도우의 가장 앞에 있는 보석
int current = 0; // 현재 슬라이딩 윈도우의 끝 인덱스
bool firstFind = false; // 처음으로 모든 종류를 포함한 윈도우를 찾았는지 여부
for(int i = 0; i < gems.size(); i++)
{
current = i;
m[gems[i]]++; // 현재 보석을 윈도우에 포함
if(m.size() == gemsCount && !firstFind) // 처음으로 모든 보석 종류를 포함한 경우
{
results.push_back({start + 1, current + 1}); // 1-based 인덱스로 저장
firstFind = true; // 첫 발견 표시
}
bool init = false;
while(m[frontGem] > 1) // 가장 앞 보석이 중복된 경우, 윈도우를 줄이기 시도
{
start++; // 시작 인덱스를 앞으로 이동
m[frontGem]--; // 해당 보석 개수 감소
frontGem = gems[start]; // 새로운 앞 보석 설정
init = true;
}
if(firstFind && init) // 줄이기 이후에도 모든 종류 포함 중이면 저장
results.push_back({start + 1, current + 1});
}
int temp = INT_MAX;
vector<int> result;
for(vector<int> v : results) // 저장된 구간 중 가장 짧은 구간 선택
{
if(temp > v[1] - v[0])
{
temp = v[1] - v[0];
result = v;
}
}
return result; // 가장 짧은 구간 반환
}
728x90
반응형
'프로그래밍 > 코딩테스트' 카테고리의 다른 글
코딩테스트 최빈값 구하기 (0) | 2025.04.24 |
---|---|
코딩테스트 : 가장 먼 노드 (0) | 2025.04.21 |
코딩테스트 : 겹치는 선분의 길이 (0) | 2025.04.21 |
코딩테스트 : 평행 (0) | 2025.04.20 |
코딩테스트 : 옹알이(1) (0) | 2025.04.20 |