题解:CF2014H Robin Hood Archery
liujinxv123 · · 题解
CF题目传送门
题目大意
Robin 和 Sheriff 比赛,Robin 先手,每次比赛他们选择 YES,否则输出 NO。
题目思路
由于 Robin 先手,为了获胜,当轮到 Robin 时他一定会选择当前剩余目标中最大分值的目标。所以无论如何 Sheriff 一定不会获胜,最多只能平局。
如果能平局,说明
剩下的便是板子了。
不会的去这里。
Code
附上完整代码。
#include <bits/stdc++.h>
using namespace std;
const int N = 1e6 + 10;
struct node{
int l,r,id;
}q[N];
int a[N];
int ans[N],cnt[N];
int n,m,sq;
bool cmp(node x,node y){
if(x.l / sq != y.l / sq) return x.l / sq < y.l / sq;
else return x.r / sq < y.r / sq;
}
int cur = 1;
void add(int p){
cnt[a[p]] ++;
if(cnt[a[p]] & 1) cur ++;
else cur --;
}
void del(int p){
cnt[a[p]] --;
if(cnt[a[p]] & 1) cur ++;
else cur --;
}
void solve(){
cur = 1;
cin >> n >> m;
sq = min((int)sqrt(n) + 1,n);
for(int i = 0;i < n;i ++){
cin >> a[i];
cnt[a[i]] = 0;
}
for(int i = 0;i < m;i ++){
cin >> q[i].l >> q[i].r;
q[i].l --;
q[i].r --;
q[i].id = i;
ans[i] = 0;
}
sort(q,q + m,cmp);
cnt[a[0]] ++;
int L = 0,R = 0;
for(int i = 0;i < m;i ++){
while(R < q[i].r) add(++ R);
while(L > q[i].l) add(-- L);
while(L < q[i].l) del(L ++);
while(R > q[i].r) del(R --);
ans[q[i].id] = cur;
}
for(int i = 0;i < m;i ++){
if(ans[i]) cout << "NO\n";
else cout << "YES\n";
}
}
int main(){
int T;
cin >> T;
while(T --) solve();
return 0;
}