문제 출처
1. 문제설명
- 자세한 설명은 문제 링크 참조
- 명령어를 구현해보자
- recommend $G$ $x$
- $x$가 1인 경우 추천 문제 리스트에서 알고리즘 분류가 $G$인 문제 중 가장 어려운 문제 번호를 출력한다.
- 조건을 만족하는 문제가 여러 개라면 그 중 문제 번호가 큰 것으로 출력한다.
- $x$가 -1인 경우 추천 문제 리스트에서 알고리즘 분류가 $G$인 문제 중 가장 쉬운 문제 번호를 출력한다.
- 조건을 만족하는 문제가 여러 개라면 그 중 문제 번호가 작은 것으로 출력한다.
- 해당 명령어는 해당 그룹 $G$에 문제 번호가 한 개 이상이 있을 경우에만 주어진다.
- recommend2 $x$
- $x$가 1인 경우 추천 문제 리스트에서 알고리즘 분류 상관없이 가장 어려운 문제 번호를 - 출력한다.
- 조건을 만족하는 문제가 여러 개라면 그 중 문제 번호가 큰 것으로 출력한다.
- $x$가 -1인 경우 추천 문제 리스트에서 알고리즘 분류 상관없이 가장 쉬운 문제 번호를 - 출력한다.
- 조건을 만족하는 문제가 여러 개라면 그 중 문제 번호가 작은 것으로 출력한다.
- recommend3 $x$ $L$
- $x$가 1인 경우 추천 문제 리스트에서 알고리즘 분류 상관없이 난이도 $L$보다 크거나 같은 문제 중 가장 쉬운 문제 번호를 출력한다.
- 조건을 만족하는 문제가 여러 개라면 그 중 문제 번호가 작은 것으로 출력한다. 만약 조건을 만족하는 문제 번호가 없다면 -1을 출력한다.
- $x$가 -1인 경우 추천 문제 리스트에서 알고리즘 분류 상관없이 난이도 $L$보다 작은 문제 중 가장 어려운 문제 번호를 출력한다.
- 조건을 만족하는 문제가 여러 개라면 그 중 문제 번호가 큰 것으로 출력한다. 만약 조건을 만족하는 문제 번호가 없다면 -1을 출력한다.
- add $P$ $L$ $G$
- 추천 문제 리스트에 난이도가 $L$이고 알고리즘 분류가 $G$인 문제 번호 $P$를 추가한다. (추천 문제 리스트에 없는 문제 번호 $P$만 입력으로 주어진다. 이전에 추천 문제 리스트에 있던 문제 번호가 다른 난이도와 다른 알고리즘 분류로 다시 들어 올 수 있다.)
- solved $P$
- 추천 문제 리스트에서 문제 번호 $P$를 제거한다. (추천 문제 리스트에 있는 문제 번호 $P$만 입력으로 주어진다.)
2. 알고리즘 설계
- set을 이용해 풀이하였다.
- 문제를 보면, 1. 알고리즘 분류 및 난이도에 따라 2. 알고리즘 난이도에 따라 로 나뉜다.
- 알고리즘 문제 번호, 분류, 난이도를 모두 담은
pair<int,int>
형 배열도 필요하다.
- 나머지는 이전 문제와 마찬가지로 iterator를 움직여주면 된다.
- 움직이는 건 이전 문제에 자세히 설명했으니 생략하겠다.
3. 전체 코드
#include <bits/stdc++.h>
using namespace std;
using pii = pair<int,int>;
int N, P, M, L, G, x;
pii problem[100'005];
set<int> lv[105];
set<int> cls_lv[105][105];
int main(){
ios::sync_with_stdio(false);
cin.tie(NULL);
cin >> N;
while(N--) {
cin >> P >> L >> G;
problem[P] = {G, L};
lv[L].insert(P);
cls_lv[G][L].insert(P);
}
cin >> M;
while(M--) {
string opt;
cin >> opt;
if(opt == "recommend") {
int num, cmp;
cin >> G >> x;
if(x == 1) {
for(int i=100; i>0; i--) {
if(cls_lv[G][i].empty()) continue;
cout << *prev(cls_lv[G][i].end()) << '\n';
break;
}
}
else {
for(int i=1; i<=100; i++) {
if(cls_lv[G][i].empty()) continue;
cout << *cls_lv[G][i].begin() << '\n';
break;
}
}
}
else if(opt == "recommend2") {
cin >> x;
if(x == 1) {
for(int i=100; i>0; i--) {
if(lv[i].empty()) continue;
cout << *prev(lv[i].end()) << '\n';
break;
}
}
else {
for(int i=1; i<=100; i++) {
if(lv[i].empty()) continue;
cout << *lv[i].begin() << '\n';
break;
}
}
}
else if(opt == "recommend3") {
int flag = false;
cin >> x >> L;
if(x == 1) {
for(int i=L; i<=100; i++) {
if(lv[i].empty()) continue;
cout << *lv[i].begin() << '\n';
flag = true;
break;
}
if(!flag) cout << "-1\n";
}
else {
for(int i=L-1; i>0; i--) {
if(lv[i].empty()) continue;
cout << *prev(lv[i].end()) << '\n';
flag = true;
break;
}
if(!flag) cout << "-1\n";
}
}
else if(opt == "add") {
cin >> P >> L >> G;
problem[P] = {G, L};
lv[L].insert(P);
cls_lv[G][L].insert(P);
}
else {
cin >> P;
pii cur = problem[P];
cls_lv[cur.first][cur.second].erase(P);
lv[cur.second].erase(P);
}
}
return 0;
}