JZOJ 5373. 【NOIP2017提高A组模拟9.17】信仰是为了虚无之人
生活随笔
收集整理的這篇文章主要介紹了
JZOJ 5373. 【NOIP2017提高A组模拟9.17】信仰是为了虚无之人
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
Description
Input
Output
Sample Input
3 3 0
1 1 7
1 1 6
1 3 2
Sample Output
1
0
1
7
0
5
Data Constraint
Solution
看到這種“真假條件”,首先要想到的就是——并查集。
設 F[x] 表示 x 的祖先,G[x] 表示從 x 到 x 的祖先的異或和。
注意:并集時編號大的要連到編號小的,這樣方便處理區間;Get_Father 時順便處理 G[x] 即可。
那么對于讀入的 l,r,k ,先查找出 l?1 和 r 的祖先 fl 和 fr 。
若 fl=fr ,則再判斷 G[l?1]?xor?G[r] 是否等于 k 即可,等于則為真,不等則為假。
若 fl≠fr ,將兩集合合并,fr 向 fl 連一條 k ,即:F[fr]=fl
G[fr]=G[l?1]?xor?G[r]?xor?k最后輸出答案,則設 sum[i] 表示從 1 到 i 的異或和,且 sum[1] 到 sum[i?1] 都已求出了。
于是顯然,第 i 為的答案就是 sum[i] xor sum[i?1]] 。那怎么求出 sum[i] 呢?
當 i 為一個集合的祖先時,說明 i 的取值不受限制,取 0 顯然最優,則:sum[i]=sum[i?1]
當 i 不為一個集合的祖先,設其祖先為 j ,那么 i 這個點要填的就是 G[i] ,于是:
sum[i]=sum[j]?xor?G[i] 。這樣的時間復雜度就是 O(M?α(N)) 。
Code
#include<cstdio> #include<algorithm> using namespace std; const int N=200001; int last; int f[N],g[N],sum[N]; inline int read() {int X=0,w=1; char ch=0;while(ch<'0' || ch>'9') {if(ch=='-') w=-1;ch=getchar();}while(ch>='0' && ch<='9') X=(X<<3)+(X<<1)+ch-'0',ch=getchar();return X*w; } inline void write(int x) {if(x>9) write(x/10);putchar(x%10+'0'); } inline int get(int x) {if(f[x]==x) return x;int y=get(f[x]);g[x]^=g[f[x]];return f[x]=y; } int main() {int n=read(),m=read(),czy=read();for(int i=1;i<=n;i++) f[i]=i;while(m--){int l=read(),r=read(),k=read();if(czy) l^=last,r^=last,k^=last;int f1=get(l-1),f2=get(r);if(f1!=f2){if(f1>f2) swap(f1,f2);f[f2]=f1;g[f2]^=g[l-1]^g[r]^k;write(last=1);}else write(last=(g[l-1]^g[r])==k);putchar('\n');}for(int i=1;i<=n;i++){int j=get(i);if(i==j) sum[i]=sum[i-1]; else sum[i]=sum[j]^g[i];write(sum[i]^sum[i-1]);putchar('\n');}return 0; }總結
以上是生活随笔為你收集整理的JZOJ 5373. 【NOIP2017提高A组模拟9.17】信仰是为了虚无之人的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: JZOJ 5372. 【NOIP2017
- 下一篇: JZOJ 5376. 【NOIP2017