题目大意:在目前积分的基础上寻找一次最佳的比赛使得一号选手排名尽可能的在前
思路解析:
虽然本题的标题是“本题又主要考察了贪心”,但不要被忽悠了哦,本题由于n和m的范围较小,适合用暴力的方法去解决。比较实用的方法是暴力搜索dfs。
有注意点提醒一下:
upper_bound()函数是在有序序列中寻找>目标值x的元素位置,返回值为指向范围 [
first,
last)
中首个符合条件的元素的迭代器,或者在找不到这种元素时返回 last(迭代器)。
求位置的话需要用返回值减掉起始迭代器
对于本题来说如果使用降序排列在某些情况下是不友好的,例如:假设一号选手在某次比赛的总积分为4,若使用降序则找到的元素为5
5 | 4 | 4 | 3 | 2 |
废话不多说,直接看代码:
#include<bits/stdc++.h>
using namespace std;
using ll = long long;
using T = pair<int, int>;
//set<int>S;
//unordered_map<int, int>mp;
const int N = 2e5 + 10;
int a[12];
int u[12];
int v[12];
int n, m;
int tmp[12];
int ans = 11;
void dfs(int i) {//i为某场比赛
if (i == m + 1) {
for (int j = 1; j <= n; ++j)tmp[j] = a[j];
int val = a[1];
sort(tmp + 1, tmp + 1 + n);
ans = min(ans, n+2-(int)(upper_bound(tmp + 1, tmp + 1 + n, val) - tmp));
return;
}
//u[i]胜
a[u[i]] += 3;
dfs(i + 1);
a[u[i]] -= 3;//回溯
//v[i]胜
a[v[i]] += 3;
dfs(i + 1);
a[v[i]] -= 3;//回溯
//平局
a[u[i]]++;
a[v[i]]++;
dfs(i + 1);
//回溯
a[u[i]]--;
a[v[i]]--;
return;
}
int main()
{
ios::sync_with_stdio(false);
cin.tie(0); cout.tie(0);
int t; cin >> t;
while (t--) {
cin >> n >> m;
int i;
for (i = 1; i <= n; ++i) {
cin >> a[i];
}
for (i = 1; i <= m; ++i) {
cin >> u[i] >> v[i];
}
ans = 11;
dfs(1);
cout << ans << endl;
}
return 0;
}