题目
A. Card Game
拥有最大value(即value为n)的一方必赢。
#include<bits/stdc++.h>
#define de(x) cout<<#x<<"= "<<x<<" "<<endl;
using namespace std;
typedef long long ll;
const ll INF=0x3f3f3f3f;
int main(){
ll t;
scanf("%lld",&t);
while(t--){
ll n,k1,k2;
scanf("%lld%lld%lld",&n,&k1,&k2);
bool flag=false;
ll x;
while(k1--){
scanf("%lld",&x);
if(x==n)
flag=true;
}
while(k2--){
scanf("%lld",&x);
}
if(flag)
printf("YES\n");
else
printf("NO\n");
}
return 0;
}
B. Interesting Subarray
若存在两个相邻的数字差的绝对值大于1,则必为yes,否则必为no
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
const ll MAXN=2e5+10;
ll t,n;
ll arr[MAXN];
int main(){
scanf("%lld",&t);
while(t--){
scanf("%lld",&n);
scanf("%lld",&arr[1]);
ll r=0;
for(int i=2;i<=n;i++){
scanf("%lld",&arr[i]);
if(arr[i]-arr[i-1]>1||arr[i]-arr[i-1]<-1){
r=i;
}
}
if(r){
printf("YES\n");
printf("%lld %lld\n",r-1,r);
}
else{
printf("NO\n");
}
}
return 0;
}
C. Make Good
可先加一个和当前异或和相等的值,使异或和为0,再加一个和现在的总和相等的值,使总和称为异或和的两倍
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
ll t,n;
ll sum,Xor,ans1,ans2;
ll x;
inline void solve(){
for(ll i=1;i<=n;i++){
scanf("%lld",&x);
sum+=x;
Xor^=x;
}
sum+=Xor;
ans1=Xor;
ans2=sum;
puts("2");
printf("%lld %lld\n",ans1,ans2);
}
int main(){
ll t;
scanf("%lld",&t);
while(t--){
scanf("%lld",&n);
sum=0;
Xor=0;
solve();
}
}
D. Strange Device
交互题,可询问长度为k+1的区间k+1次,则只会有两个结果,分别是这个区间内第m小和第m+1小,第m+1小的数在这k+1次讯问中出现的次数即为m的值。
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
int main(){
ll n,k;
scanf("%lld%lld",&n,&k);
ll cnta=0,cntb=0,a=-1,b=-1;
for(ll i=1;i<=k+1;i++){
printf("?");
for(ll j=1;j<=k+1;j++){
if(j!=i){
printf(" %lld",j);
}
}
printf("\n");
ll x,y;
cout.flush();
scanf("%lld%lld",&x,&y);
if(a==-1){
a=y;
cnta++;
}
else if(y==a){
cnta++;
}
else if(b==-1){
b=y;
cntb++;
}
else{
cntb++;
}
}
ll m;
if(a<b)
m=cntb;
else
m=cnta;
printf("! %lld\n",m);
return 0;
}
E. Divide Points
点的坐标可分为奇偶、奇奇、偶奇、偶偶四种情况,分成两个集合,使集合内部的欧几里得距离和集合之间的欧几里得距离不存在相等的情况,可以横纵坐标的和为奇还是为偶为界限将坐标分进AB两个集合,若两个集合都不为空,则满足条件,直接输出其中一个集合即可。若有一个集合为空,则需进行如下操作:若所有点横纵坐标和全为奇数,则先将所有点的横纵标-1(不会使相等变不等,也不会使不等变相等);然后将所有点横坐标x变为(x+y)/2,将纵坐标变为(x-y)/2,这样欧式距离变为原来的1/2,也不会改变原有的相等性,然后重新进行一开始的操作,直到符合条件,输出即可。
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
const ll MAXN=1e3+10;
vector<ll>vec;
ll a[MAXN],b[MAXN];
int main(){
ll n;
scanf("%lld",&n);
for(int i=1;i<=n;i++){
scanf("%lld%lld",&a[i],&b[i]);
}
while(true){
for(int i=1;i<=n;i++){
if((a[i]+b[i])&1){
vec.push_back(i);
}
}
ll sz=vec.size();
if(sz!=n&&sz!=0){
printf("%lld\n",sz);
for(int i=0;i<sz;i++){
printf("%lld%c",vec[i],i==sz-1?'\n':' ');
}
return 0;
}
if(sz==n){
vec.clear();
for(ll i=1;i<=n;i++){
a[i]--;
}
}
for(int i=1;i<=n;i++){
ll x=(a[i]+b[i])/2;
ll y=(a[i]-b[i])/2;
a[i]=x;
b[i]=y;
}
}
return 0;
}