AT5140 [AGC035C] Skolem XOR Tree 題解
阿新 • • 發佈:2021-11-11
link
AT5140 [AGC035C] Skolem XOR Tree
給定一個正整數 \(N\)
試判斷,是否存在這樣一棵節點數為 \(2N\) 的樹,滿足:
-
\(∀i∈[1,n]\),第 \(i\) 號節點和第 \(i+n\) 號節點的權值均為 \(i\)
-
第 \(i\) 號節點到第 \(i+N\) 號節點路徑上的點的點權異或和恰為 \(i\)
sol
試考慮異或的性質 : $0 ⨁x=x $
也就是說,對於一對 \(i,n+i\) 要構造出,除了 \(i\) 以外一直到 \(n+i\) 的異或和為 \(0\) (包括 \(n+i\))
所以考慮 \(2n+1⨁2n=1\) 這個答案再異或上 \(1\)
所以我們可以講 \(i\)和 \(i+1\) 看成一對來處理,一對 \(i,i+1,2n+i,2n+i+1\) 我們可以這樣連
\(i+1--i --1--2n+i+1--2n+i\)
這樣成對就可以滿足了
然後考慮 \(1\) 怎麼連,我們發現 \(1⨁2⨁3=0\),所以利用前面的性質
$1--2--3--n+1--n+2--n+3$6
如果 \(n\) 是偶數的話,上面的情況 \(n\)和 \(2n\) 是無法處理的
那麼我們就要找一條經過 \(1\) 的路徑 ,滿足 \(x⨁y⨁1=n\) 那麼將 \(n\) 連 \(x\) 連 \(1\) 連 \(y\) 連 \(2n\)
通過觀察樣例我們發現,如果 \(n\) 是 \(2\) 的整數次冪無解,因為只有 \(n\) 的最高位是 \(1\) ,比 \(n\) 小的數不可能將最高位構造出 \(1\)
code
#include<bits/stdc++.h> using namespace std; int n,m; int main(){ freopen("AT5140.in","r",stdin); freopen("AT5140.out","w",stdout); scanf("%d",&n);m=log2(n); if(!((1<<m)^n))return printf("No\n"),0; printf("Yes\n"); printf("%d %d\n",1,2); printf("%d %d\n",2,3); printf("%d %d\n",3,n+1); printf("%d %d\n",n+1,n+2); printf("%d %d\n",n+2,n+3); for(int i=2;2*i+1<=n;i++){ printf("%d %d\n",1,2*i); printf("%d %d\n",1,2*i+1); printf("%d %d\n",2*i,2*i+n+1); printf("%d %d\n",2*i+1,2*i+n); } if(!(n&1)){ for(int i=2;i<=n;i++){ if(i==3) continue; int y=(i^1^n); if(y==3||y>n) continue; printf("%d %d\n",n,i); printf("%d %d\n",2*n,y); break; } } return 0; }