QOJ.ac
QOJ
ID | Problem | Submitter | Result | Time | Memory | Language | File size | Submit time | Judge time |
---|---|---|---|---|---|---|---|---|---|
#758023 | #9570. Binary Tree | piaoyun# | RE | 2ms | 5896kb | C++14 | 3.9kb | 2024-11-17 15:10:36 | 2024-11-17 15:10:38 |
Judging History
answer
#include<bits/stdc++.h>
using namespace std;
int query(int x, int y){
cout << "? " << x << " " << y << endl;
cout.flush();
cin >> x;
return x;
}
vector<int> adj[100005];
bool vis[100005];
int T,n;
int sz;
void add(int x, int y){
// cout << "add " << x << " " << y << endl;
adj[x].push_back(y);
adj[y].push_back(x);
}
void Free(int x, int fa){
if(!vis[x]) sz --;
vis[x] = true;
for(int y: adj[x]){
if(y == fa) continue;
Free(y, x);
}
}
int mn,centre = 0;
int sum[100005];
int tot = 0;
int father[100005];
void dfs(int u,int fa){
// cout << "123\n";
father[u] = fa;
if(vis[u]){
sum[u] = 0;
return;
}
sum[u] = 1;
for(auto v : adj[u]){
if(v == fa) continue;
dfs(v,u);
sum[u] += sum[v];
}
}
void get_centre(int u,int fa){
if(vis[u]) return;
int mx = 0;
for(auto v : adj[u]){
if(v == fa) continue;
get_centre(v,u);
mx = max(mx, sum[v]);
}
if(u != fa){
mx = max(mx , tot - sum[u]);
}
// cout << u << " " << mx << endl;
if(mx < mn){
mn = mx;
centre = u;
}
}
int Find(int S){
// cout << "haha\n";
mn = 1e9;
dfs(S,S);
tot = sum[S];
get_centre(S,S);
// cout << centre << " " << mn << endl;
return centre;
}
vector<int> get_adj(int x){
vector<int> ret;
for(int i: adj[x]){
if(!vis[i]) ret.push_back(i);
}
// for(int x: ret) cout << x << "#";
return ret;
}
int main(){
cin >> T;
while(T--){
cin >> n;
for(int i=1;i<=n;i++) vis[i] = false;
for(int i=1;i<=n;i++) adj[i].clear();
for(int i=1;i<=n;i++){
int l,r;
cin >> l >> r;
if(l) add(i, l);
if(r) add(i, r);
}
sz = n;
while(sz > 3){
// cout << "alive: \n";
// for(int i=1;i<=n;i++){
// if(!vis[i]) cout << i << " ";
// }
int alive = -1;
for(int i=1;i<=n;i++)
if(!vis[i]){
alive = i;
break;
}
int x = Find(alive);
vector<int> v = get_adj(x);
assert(v.size() >= 2);
int a = v[0], b = v[1];
int res = query(a, b);
if(res == 0){
Free(b, x);
if(v.size() > 2){
int c = v[2];
Free(c, x);
}
vis[x] = true;
sz --;
}
else if(res == 1){
Free(b, x);
Free(a, x);
}
else{
// res = 2
Free(a, x);
if(v.size() > 2){
int c = v[2];
Free(c, x);
}
vis[x] = true;
sz --;
}
}
int ans = -1;
vector<int> v;
for(int i=1;i<=n;i++) if(!vis[i]) v.push_back(i);
if(v.size() == 1){
ans = v[0];
}
else if(v.size() == 2){
int x = v[0], y = v[1];
int res = query(x,y);
if(res == 0) ans = x;
else ans = y;
}
else if(v.size() == 3){
int x = v[0], y = v[1];
int mid = Find(x);
x = y = -1;
for(int i: v){
if(i != mid){
if(x == -1) x = i;
else y = i;
}
}
int res = query(x,y);
if(res == 0) ans = x;
else if(res == 1) ans = mid;
else ans = y;
}
cout << "! " << ans << endl;
cout.flush();
}
}
Details
Tip: Click on the bar to expand more detailed information
Test #1:
score: 100
Accepted
time: 2ms
memory: 5896kb
input:
2 5 0 0 1 5 2 4 0 0 0 0 1 1 2 0 2 0 0 2
output:
? 1 5 ? 2 4 ! 3 ? 1 2 ! 2
result:
ok OK (2 test cases)
Test #2:
score: -100
Runtime Error
input:
5555 8 2 0 8 6 0 0 3 0 0 0 7 0 0 0 5 4 0 0 2 8 0 0 1 4 2 0 0 0 7 8 0 0 3 0 6 0 2 1 0 8 5 8 0 0 1 7 0 0 0 0 4 2 0 0 6 0 0 0 2 5 4 5 3 1 0 0 0 0 0 0 1 2 8 0 0 0 0 5 6 0 0 1 4 2 0 3 8 0 0 0 0 5 3 0 5 1 0 0 0 0 4 0 0 2 5 5 0 0 0 0 0 3 0 2 4 1 0 3 3 0 1 0 0 0 2 2 2 0 0 0 0 3 2 3 0 0 0 0 2 10 2 8 9 7 0 0 ...
output:
? 2 5 ? 2 7 ? 1 2 ! 2 ? 5 3 ? 1 4 ? 2 3 ! 2 ? 1 6 ? 1 7 ? 1 5 ! 5 ? 4 5 ? 1 3 ! 3 ? 5 6 ? 1 4 ! 1 ? 5 1 ? 4 5 ! 5 ? 1 2 ? 3 5 ! 3 ? 2 3 ! 3 ? 1 2 ! 1 ? 2 3 ! 3 ? 2 6 ? 1 9 ? 9 10 ! 10 ? 1 2 ! 1 ? 5 9 ? 4 8 ? 3 5 ! 3 ? 5 8 ? 7 1 ? 3 5 ! 3 ? 3 4 ? 1 7 ? 2 8 ! 8 ? 1 2 ! 2 ? 4 3 ? 1 7 ! 7 ? 4 9 ? 2 3 ? ...