Odd-Even Subsequence T17 D57
Problem - D - Codeforces (Unofficial mirror site, accelerated for Chinese users)
思路
交互题
将每条边按dfs序保存起来。
每次询问一半的边,若询问的值不等于最大值,递归另一半。
参考代码
#include<bits/stdc++.h>
#define ll long long
#define pii pair<int,int>
#define fi first
#define se second
#define pb push_back
#define si size()
#define ls (p<<1)
#define rs ((p<<1)|1)
#define mid (t[p].l+t[p].r)/2
using namespace std;
ll read(){ll x=0,f=1;char ch=getchar();while(ch<'0'||ch>'9'){if(ch=='-') f=-1;ch=getchar();}while(ch>='0'&&ch<='9'){x=(x<<1)+(x<<3)+(ch^48);ch=getchar();}return x*f;}
inline void Prin(ll x){if(x < 0){putchar('-');x = -x;}if(x > 9) Prin(x / 10);putchar(x % 10 + '0');}
const int inf=0x3f3f3f3f;
const ll mod=1000000007;
const int qs=2e3+7;
int T,n,k,a[qs],cnt=0;
int u[qs];
vector< int > v[qs];
vector< pii > ans;
void dfs(int x,int fa){
for(int i=0;i<v[x].si;++i){
int p=v[x][i];
if(p==fa) continue;
ans.pb({x,p});
dfs(p,x);
}
}
int Max=0;
void solve(int l,int r){
if(l==r){
cout<<"! "<<ans[l].fi<<" "<<ans[l].se<<"\n";
cout.flush();
return;
}
int md=(l+r)/2;
int cnt=0;
cout<<"?";
for(int i=l;i<=md;++i){
a[++cnt]=ans[i].fi,a[++cnt]=ans[i].se;
}
sort(a+1,a+1+cnt);
cnt=unique(a+1,a+1+cnt)-a-1;
cout<<" "<<cnt;
for(int i=1;i<=cnt;++i) cout<<" "<<a[i];
cout<<"\n";
cout.flush();
int ft;
cin>>ft;
if(ft==Max){
Max=ft;
solve(l,md);
}
else{
solve(md+1,r);
}
}
int main(){
cin>>n;
int x,y;
for(int i=1;i<n;++i){
cin>>x>>y;
v[x].pb(y);
v[y].pb(x);
}
dfs(1,0);
cout<<"?";
cout<<" "<<n;
for(int i=1;i<=n;++i) cout<<" "<<i;
cout<<"\n";
cout.flush();
cin>>Max;
solve(0,ans.size()-1);
return 0;
}