Description
There are three types of animals in the animal kingdom, A, B, and C. The food chain of these three types of animals forms an interesting ring. A eats B, B eats C, and C eats A.
There are currently N animals, numbered from 1 to N. Every animal is one of A, B, and C, but we don't know which one it is.
Some people describe the food chain relationship formed by these N animals in two ways: the
first one is "1 X Y", which means that X and Y are of the same kind.
The second argument is "2 X Y", which means X eats Y.
This person uses the above two statements to say K sentences to N animals one after another. Some of these K sentences are true and some are false. When a sentence satisfies one of the following three items, the sentence is false, otherwise it is true.
1) The current words conflict with some previous true words, which is a lie;
2) The current words X or Y is greater than N, which is a lie;
3) The current words mean that X eats X, which is a lie.
Your task is to output the total number of lies based on a given N (1 <= N <= 50,000) and K sentences (0 <= K <= 100,000).
Input
The first line is two integers N and K, separated by a space.
Each of the following K lines is three positive integers D, X, Y, separated by a space between the two numbers, where D represents the type of argument.
If D=1, it means that X and Y are of the same kind.
If D=2, it means X eats Y.
Output
There is only one integer, which represents the number of lies.
Sample Input
100 7
1 101 1
2 1 2
2 2 3
2 3 3
1 1 3
2 3 1
1 5 5
Sample Output
3
There are three kinds of ideas , so create a union search set with a size of 3N, representing A, B, and C.
If xy belongs to the same category, merge xA and yA, xB and yB, and xC and yC.
If x eats y, then xA yB, xB yC, xC yA.
Code
int T[K+1],X[K+1],Y[K+1];
void solve(){
init(3*N);
int ans=0;
//读入信息
for(int i=0;i<K;i++){
int t=T[i];
int x=X[i]-1,y=Y[i]-1;
if(x<0||N<=x||y<0||N<=y){
ans++;continue;}
if(t==1){
//非同类
if(same(x,y+N)||same(x,y+2*N)){
ans++;
}
else{
merge(x,y);
merge(x+N,y+N);
merge(x+2*N,y+2*N);
}
}
else{
//xy同类或x被y吃
if(same(x,y)||same(x,y+2*N)){
ans++;
}
else{
merge(x,y+N);
merge(x+N,y+2*N);
merge(x+2*N,y);
}
}
}
}