当前位置:网站首页>Parallel search exercise 1: circle of friends

Parallel search exercise 1: circle of friends

2022-06-21 22:52:00 yitahutu79

Title Description
​ A circle of friends , Not all of them know each other directly .

​ for example : Xiao Zhang's friend is Xiao Li , Xiao Li's friend is Xiao Wang , Then the three of them belong to a circle of friends .

​ Now give some people's friends , People follow from 1 To n In the middle of this, the number will ask whether two people belong to a circle of friends , Please write a program , To achieve this process .

Input
Enter two integers on the first line n,m(1≤n≤10000,3≤m≤100000), Represent the number of people and operands respectively .

Next m That's ok , Three whole... Per line a,b,c(a∈[1,2], 1≤b,c≤n)
When a=1 when , Represents adding a new piece of known information ,b,c It's a friend.
When a=2 when , According to the above information , inquiry b,c Whether it's a friend
Output
For each a=2 The operation of , Output 『Yes』 or 『No』 The representative asked whether the two people were friends .

The sample input

6 5
1 1 2
2 1 3
1 2 4
1 4 3
2 1 3

Sample output

No
Yes

Data scale and agreement
The time limit :1 s

Memory limit :64 M

100% Data assurance for n,m(1≤n≤10000,3≤m≤100000)

Method :
1.quick_find

#include <stdio.h>
#include <stdlib.h>

typedef struct UnionSet {
    
	int* color;
	int n;
}UnionSet;

UnionSet* init(int n) {
    
	UnionSet* u = (UnionSet*)malloc(sizeof(UnionSet));
	u->color = (int*)malloc(sizeof(int) * (n + 1));
	for (int i = 1; i <= n; i++) {
    
		u->color[i] = i;
	}
	u->n = n;
	return u;
}

int find(UnionSet* u, int x) {
    
	return u->color[x];
}

int merge(UnionSet* u, int a, int b) {
    
	if (find(u, a) == find(u, b)) return 0;
	int color_a = u->color[a];
	for (int i = 1; i <= u->n; i++) {
    
		if (u->color[i] - color_a) continue;
		u->color[i] = u->color[b];
	}
	return 1;
}

void clear(UnionSet* u) {
    
	if (u == NULL) return;
	free(u->color);
	free(u);
	return;
}

int main() {
    
	int n, m;
	scanf("%d%d", &n, &m);
	UnionSet* u = init(n);
	for (int i = 0; i < m; i++) {
    
		int a, b, c;
		scanf("%d%d%d", &a, &b, &c);
		switch (a) {
    
		case 1: merge(u, b, c); break;
		case 2:printf("%s\n", find(u, b) == find(u, c) ? "Yes" : "No"); break;
		}
	}
	clear(u);
	return 0;
}

 Insert picture description here
 Insert picture description here

2.quick_union

#include <stdio.h>
#include <stdlib.h>

typedef struct UnionSet {
    
	int* father;
	int n;
}UnionSet;

UnionSet* init(int n) {
    
	UnionSet* u = (UnionSet*)malloc(sizeof(UnionSet));
	u->father = (int*)malloc(sizeof(int) * (n + 1));
	for (int i = 1; i <= n; i++) {
    
		u->father[i] = i;
	}
	u->n = n;
	return u;
}

int find(UnionSet* u, int x) {
    
	if (u->father[x] == x) return x;
	return find(u, u->father[x]);
}

int merge(UnionSet* u, int a, int b) {
    
	int fa =find(u, a), fb = find(u, b);
	if (fa == fb) return 0;
	u->father[fa] = fb;
	return 1;
}

void clear(UnionSet* u) {
    
	if (u == NULL) return;
	free(u->father);
	free(u);
	return;
}

int main() {
    
	int n, m;
	scanf("%d%d", &n, &m);
	UnionSet* u = init(n);
	for (int i = 0; i < m; i++) {
    
		int a, b, c;
		scanf("%d%d%d", &a, &b, &c);
		switch (a) {
    
		case 1: merge(u, b, c); break;
		case 2:printf("%s\n", find(u, b) == find(u, c) ? "Yes" : "No"); break;
		}
	}
	clear(u);
	return 0;
}

 Insert picture description here
 Insert picture description here

  1. Optimize 1:weighted quick_union
#include <stdio.h>
#include <stdlib.h>

#define swap(a,b) {
      \ a ^= b,b ^= a, a ^= b;\ }
typedef struct UnionSet {
    
	int* father, *size;
	int n;
}UnionSet;

UnionSet* init(int n) {
    
	UnionSet* u = (UnionSet*)malloc(sizeof(UnionSet));
	u->father = (int*)malloc(sizeof(int) * (n + 1));
	u->size = (int*)malloc(sizeof(int) * (n + 1));
	for (int i = 1; i <= n; i++) {
    
		u->father[i] = i;
		u->size[i] = 1;
	}
	u->n = n;
	return u;
}

int find(UnionSet* u, int x) {
    
	if (u->father[x] == x) return x;
	return find(u, u->father[x]);
}

int merge(UnionSet* u, int a, int b) {
    
	int fa =find(u, a), fb = find(u, b);
	if (fa == fb) return 0;
	if (u->size[fa] < u->size[fb]) swap(fa, fb);
	u->father[fb] = fa;
	u->size[fa] += u->size[fb];
	return 1;
}

void clear(UnionSet* u) {
    
	if (u == NULL) return;
	free(u->father);
	free(u->size);
	free(u);
	return;
}

int main() {
    
	int n, m;
	scanf("%d%d", &n, &m);
	UnionSet* u = init(n);
	for (int i = 0; i < m; i++) {
    
		int a, b, c;
		scanf("%d%d%d", &a, &b, &c);
		switch (a) {
    
		case 1: merge(u, b, c); break;
		case 2:printf("%s\n", find(u, b) == find(u, c) ? "Yes" : "No"); break;
		}
	}
	clear(u);
	return 0;
}

 Insert picture description here
 Insert picture description here

  1. Optimize 2: Path compression + weighted quick_union
#include <stdio.h>
#include <stdlib.h>

#define swap(a,b) {
      \ a ^= b,b ^= a, a ^= b;\ }
typedef struct UnionSet {
    
	int* father, *size;
	int n;
}UnionSet;

UnionSet* init(int n) {
    
	UnionSet* u = (UnionSet*)malloc(sizeof(UnionSet));
	u->father = (int*)malloc(sizeof(int) * (n + 1));
	u->size = (int*)malloc(sizeof(int) * (n + 1));
	for (int i = 1; i <= n; i++) {
    
		u->father[i] = i;
		u->size[i] = 1;
	}
	u->n = n;
	return u;
}

int find(UnionSet* u, int x) {
    
	if (u->father[x] == x) return x;
	return u->father[x] = find(u, u->father[x]);
}

int merge(UnionSet* u, int a, int b) {
    
	int fa =find(u, a), fb = find(u, b);
	if (fa == fb) return 0;
	if (u->size[fa] < u->size[fb]) swap(fa, fb);
	u->father[fb] = fa;
	u->size[fa] += u->size[fb];
	return 1;
}

void clear(UnionSet* u) {
    
	if (u == NULL) return;
	free(u->father);
	free(u->size);
	free(u);
	return;
}

int main() {
    
	int n, m;
	scanf("%d%d", &n, &m);
	UnionSet* u = init(n);
	for (int i = 0; i < m; i++) {
    
		int a, b, c;
		scanf("%d%d%d", &a, &b, &c);
		switch (a) {
    
		case 1: merge(u, b, c); break;
		case 2:printf("%s\n", find(u, b) == find(u, c) ? "Yes" : "No"); break;
		}
	}
	clear(u);
	return 0;
}

 Insert picture description here
 Insert picture description here

  1. Optimize 3: Path compression quick_union
#include <stdio.h>
#include <stdlib.h>


typedef struct UnionSet {
    
	int* father;
	int n;
}UnionSet;

UnionSet* init(int n) {
    
	UnionSet* u = (UnionSet*)malloc(sizeof(UnionSet));
	u->father = (int*)malloc(sizeof(int) * (n + 1));
	for (int i = 1; i <= n; i++) {
    
		u->father[i] = i;
	}
	u->n = n;
	return u;
}

int find(UnionSet* u, int x) {
    
	if (u->father[x] == x) return x;
	return u->father[x] = find(u, u->father[x]);
}

int merge(UnionSet* u, int a, int b) {
    
	int fa =find(u, a), fb = find(u, b);
	if (fa == fb) return 0;
	u->father[fb] = fa;
	return 1;
}

void clear(UnionSet* u) {
    
	if (u == NULL) return;
	free(u->father);
	free(u);
	return;
}

int main() {
    
	int n, m;
	scanf("%d%d", &n, &m);
	UnionSet* u = init(n);
	for (int i = 0; i < m; i++) {
    
		int a, b, c;
		scanf("%d%d%d", &a, &b, &c);
		switch (a) {
    
		case 1: merge(u, b, c); break;
		case 2:printf("%s\n", find(u, b) == find(u, c) ? "Yes" : "No"); break;
		}
	}
	clear(u);
	return 0;
}

 Insert picture description here

原网站

版权声明
本文为[yitahutu79]所创,转载请带上原文链接,感谢
https://yzsam.com/2022/172/202206212101584911.html