【1012 25 预处理】 The Best Rank

传送门

题意

给定 \(n\) 个考⽣的 \(3\) ⻔分数,平均分根据这三⻔算出来。然后分别对这四个分数从⾼到低排序,这样对每个考⽣生来说有 \(4\) 个排名。\(m\) 个查询,对于每⼀个学⽣ \(id\),输出当前 \(id\) 学⽣的最好的排名和它对应的分数,如果名次相同,按照 $A>C>M>E $ 的顺序输出~如果当前 \(id\) 不存在,输出 \(N/A\)

数据范围

\(0 < m \leq 2000\)

题解

  • ump<ll, ump<char, ll>> rank 第一个 key 存的是 id, 第二个存科目标记,第二个 value 存的是排名
  • ump<char, vi<pld> rank 存的是每一科的所有学生成绩,pair 存储 id 和成绩
  • 对每个科目的进行排序,将每个学生这个科目的排名存入
  • 对于询问的学生找到 rank 最高的科目输出

Code

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

#define ll long long
#define fi first
#define se second

double eps = 1e-7;
int main() {
	ll n, m; cin >> n >> m;
	unordered_map<ll, unordered_map<char, ll>> rank;
	unordered_map<char, vector<pair<ll, double>>> subjects;

	for (int i = 0; i < n; i++) {
		ll id; cin >> id;
		double sum = 0;
		for (char c : {'C', 'M', 'E'}) {
			int x; cin >> x;
			sum += x;
			subjects[c].push_back({id, x});
		}
		subjects['A'].push_back({id, sum / 3});
	}

	for (auto& it : subjects){
		auto& c = it.fi;
		auto& grades = it.se;

		sort(grades.begin(), grades.end(), 
			[](const pair<ll, double>& a, const pair<ll, double>& b){
				return a.se > b.se;
			});

		ll r = 1;
		for (int i = 0; i < grades.size(); i++) {
			auto& x = grades[i];
			if (not i or abs(x.se - grades[i - 1].se) > eps) r = i + 1;
			rank[x.fi][c] = r;
		}
	}
	for (int i = 0; i < m; i++) {
		int id; cin >> id;
		if (not rank.count(id)) {
			cout << "N/A" << endl;
			continue;
		}
		char c = 'A';
		for (char x : {'A', 'C', 'M', 'E'}) {
			if (rank[id][x] < rank[id][c]) c = x;
		}
		cout << rank[id][c] << ' ' << c << endl;
	}
}
posted @ 2021-01-26 18:24  Hyx'  阅读(56)  评论(0)    收藏  举报