문제 링크: https://www.acmicpc.net/problem/11946

 

채점 로그를 입력받는 동시에 딱 한번만 순회해서 문제를 풀 수 있습니다.

팀 구조체를 만든 다음에 문제 별로 풀었는지 체크하는 배열과 문제 별 페널티 배열을 만들어서 쓰면 됩니다. 그럼 귀찮게 채점 로그를 어디다 담아두고 여러번 순회할 일이 없죠

#pragma GCC optimize ("Ofast")

#include <bits/stdc++.h>
using namespace std;


struct team {
	int solved_cnt;
	int penalty;
	int idx;
	vector<int> pending_penalty;
	vector<bool> solved_chk;

	team(int probs) : pending_penalty(probs), solved_chk(probs) {
		solved_cnt = penalty = 0;
	}
};


int main() {
	ios_base::sync_with_stdio(false);
	cin.tie(nullptr), cout.tie(nullptr);

	int n, m, q;
	cin >> n >> m >> q;

	vector<team> teams(n, team(m));
	for (int i = 0; i < n; ++i)
		teams[i].idx = i + 1;

	while (q--) {
		int t, idx, prob;
		string res;
		cin >> t >> idx >> prob >> res;

		--idx, --prob;

		if (!teams[idx].solved_chk[prob]) {
			if (res == "AC") {
				teams[idx].solved_chk[prob] = true;
				teams[idx].penalty += t + teams[idx].pending_penalty[prob];
				++teams[idx].solved_cnt;
			}
			else {
				teams[idx].pending_penalty[prob] += 20;
			}
		}
	}

	sort(teams.begin(), teams.end(), [](const team& t1, const team& t2) {
		if (t1.solved_cnt != t2.solved_cnt)
			return t1.solved_cnt > t2.solved_cnt;
		if (t1.penalty != t2.penalty)
			return t1.penalty < t2.penalty;
		return t1.idx < t2.idx;
	});

	for (auto& t : teams)
		cout << t.idx << ' ' << t.solved_cnt << ' ' << t.penalty << '\n';
	
	return 0;
}
반응형