Doby's Lab

[C++] 백준 1620번: 나는야 포켓몬 마스터 이다솜, 새로운 STL, map 본문

C++

[C++] 백준 1620번: 나는야 포켓몬 마스터 이다솜, 새로운 STL, map

도비(Doby) 2021. 10. 25. 17:35

이 문제는 전제가 좀 길다.

결론적으로 다음 단어들을 입력하고, 숫자를 입력하면 이름을, 이름을 입력하면 숫자를 출력하는 문제이다.

당연히 pair형 vector배열을 선언하여 풀려고 했지만 string을 입력했을 때는 어떻게 숫자 값을 도출할지가 문제였다.

여기서 사용된 것이 C++의 STL map이다.


STL <map>

map은 <map>이라는 헤더 파일에 선언되어있다. 

map<key, value> m;

이런 방법으로 선언하여 key값과 value에 원하는 타입형을 선언하여 사용할 수 있다. 데이터를 삽입/삭제/찾기 시간 복잡도 모두 O(log N)이다. 같은 key값에 value를 삽입할 경우 기존에 있던 value값은 삭제된다. (해시 맵과는 다른 듯하다.)

 

삽입하는 방식은

m.insert(make_pair(key, value));

pair를 삽입하는 방법과 유사하다.

 

이러한 부분에서 map만이 가지고 있는 특이한 특성을 알 수 있었다. 기존의 배열이라면 인덱스 번호를 알고 있어야 그에 해당하는 데이터 값을 가져올 수 있었는데 map은 key의 방식으로 원하는 타입의 key를 선언하기 때문에 key가 string 형태이면 m[string 타입 인덱스]를 불러오면 그에 해당하는 value값을 가져올 수 있다는 게 신기했다.


소스 코드

이러한 map의 특성을 활용하여 문제를 풀어나갔다.

앞서 말한 대로 'string형태의 입력값이 들어오면 어쩌지'라는 고민은 map을 두 개(key가 int, 다른 하나는 string) 선언하여 문제를 풀 수 있었다. 두 개의 map에다가 데이터를 받고, 문자열의 형태로 입력값을 받으면 입력값이 숫자인지 문자인지 판별하여 그에 따른 value 값을 출력하는 식으로 문제를 풀었다.

#include <iostream>
#include <vector>
#include <utility>
#include <string>
#include <map>
using namespace std;

int main() {
	ios_base::sync_with_stdio(false);
	cin.tie(NULL);
	int n, m;
	cin >> n >> m;

	map<int, string> m1;
	map<string, int> m2;
	m1.insert(make_pair(0, "empty"));
	m2.insert(make_pair("empty", 0));
	for (int i = 1; i <= n; i++) {
		string idx;
		cin >> idx;
		m1.insert(make_pair(i, idx));
		m2.insert(make_pair(idx, i));
	}

	for (int i = 0; i < m; i++) {
		string idx;
		cin >> idx;
		if (idx[0] < 'A') {
			int idx2 = stoi(idx);
			cout << m1[idx2] << '\n';
		}
		else {
			cout << m2[idx] << '\n';
		}
	}

	return 0;
}

보완해야 할 점

새로운 STL map을 배웠지만 다른 map관련 문제를 풀면서 새로운 문법(?)을 공부해야 한다는 생각이 들었다.

[다른 문제를 풀다가 쓴 코드]

vector<int> arr;
for (auto j = m.begin(); j != m.end(); j++) {
	arr.push_back(j->second);
}

auto는 아무래도 변수에 따른 타입형을 자동으로 정해주는 거라면 iter(반복자), ->의 의미 등 아직 공부해야 할 것들이 많다.

728x90