알고리즘

BOJ 21944: 문제 추천 시스템 Version 2

minbear 2023. 7. 18. 00:36

#BOJ 21944: 문제 추천 시스템 Version 2

 

21944번: 문제 추천 시스템 Version 2

recommend, recommend2, recommend3 명령이 주어질 때마다 문제 번호를 한 줄씩 출력한다. 주어지는 recommend, recommend2, recommend3 명령어의 총 개수는 최소 1개 이상이다.

www.acmicpc.net

#풀이

BOJ21939 와 비슷하지만 조금 추가 된 문제이다.

 

문제, 난이도, 분류 3가지를 입력

1. recommend

2. recommend2

3. recommend3

4. add

5. solved

 

BOJ21939와 비슷하게

문제 와 난이도 map, 난이도에 따른 문제 set,  문제와 분류 map 분류에 따른 문제 set을 사용하였다.

 

set 특성상 정렬되어 있기 때문에 문제 번호를 찾기 쉽다.

 

 

#코드

#include<iostream>
#include<set>
#include<unordered_map>
#include<string>
#define X first
#define Y second
using namespace std;
int n, p ,m, l, g;
set<int> que[102]; // 난이도별로 문제 저장
set <int> type[102];
unordered_map<int, int> que_; // 문제번호를 통해서 난이도 검색
unordered_map<int, int>type_;

void recommend(int G, int x) {
	if (x == 1) {
		for (int i = 100; i >= 1; i--) {
			if (que[i].size() == 0)
				continue;
			auto a = prev(que[i].end());
			while (1)
			{
				if (type[G].find(*a) != type[G].end())
				{
					cout << *a << '\n';
					return;
				}
				if (a == que[i].begin())
					break;
				a = prev(a);
			}
		}
	}
	else {
		for (int i = 1; i <= 100; i++) {
			if (que[i].size() == 0)
				continue;
			auto a = que[i].begin();
			while (1)
			{
				if (a == que[i].end())
					break;
				if (type[G].find(*a) != type[G].end())
				{
					cout << *a << '\n';
					return;
				}
				
				a = next(a);
			}
		}
	}

}

void recommend2(int x) {
	if (x == 1) {
		for (int i = 100; i >= 1; i--) {
			if (que[i].size() == 0)
				continue;
			auto a = prev(que[i].end());
			cout << *a << '\n';
			return;
		}
	}
	else {
		for (int i = 1; i <= 100; i++) {
			if (que[i].size() == 0)
				continue;
			auto a = que[i].begin();
			cout << *a << '\n';
			return;
		}
	}
}

void recommend3(int x, int L) {
	if (x == 1) {
		for (int i = L; i <= 100; i++) {
			if (que[i].size() == 0)
				continue;
			auto a = que[i].begin();
			cout << *a << '\n';
			return;
		}
		
	}
	else {
		for (int i = L-1; i >= 1; i--) {
			if (que[i].size() == 0)
				continue;
			auto a = prev(que[i].end());
			cout << *a << '\n';
			return;
		}
	}
	cout << -1 << '\n';
}

void add(int num, int diff, int G) {
	if (que_.find(num) != que_.end())
	{
		if (que_[num] != diff)
		{
			int prev = que_[num];
			que[prev].erase(num);
			que_[num] = diff;
			que[diff].insert(num);

		}

		if (type_[num] != G) {
			int prev = type_[num];
			type[prev].erase(num);
			type_[num] = G;
			type[G].insert(num);
		}
	}
	else {
		que_[num] = diff;
		que[diff].insert(num);
		type_[num] = G;
		type[G].insert(num);
	}

}

void solve(int num) {
	int diff = que_[num];
	int que_type = type_[num];
	que[diff].erase(num);
	que_.erase(num);
	type[que_type].erase(num);
	type_.erase(num);

}
int main() {
	ios::sync_with_stdio(0);
	cin.tie(0);
	cin >> n;
	for (int i = 0; i < n; i++) {
		cin >> p >> l >> g;
		que[l].insert(p);
		que_[p] = l;
		type[g].insert(p);
		type_[p] = g;
	}
	
	cin >> m;
	for (int i = 0; i < m; i++) {
		string str;
		cin >> str;
		if (str == "recommend") {
			cin >> p >> l;
			recommend(p, l);

		}
		else if (str == "recommend2") {
			cin >> p;
			recommend2(p);

		}
		else if (str == "recommend3") {
			cin >> p >> l;
			recommend3(p, l);
		}
		else if (str == "add") {
			cin >> p >> l >> g;
			add(p, l, g);
		}
		else { // solved
			cin >> p;
			solve(p);
		}
	}
	return 0;
}