C++ 并查集

几个并查集的C++实现

1、接口UF.h

#pragma once
class UF {
public:
	virtual int GetSize() = 0;
	virtual bool IsConnected(int p,int q) = 0;
	virtual void UnionElements(int p,int q) = 0;
};

2、几种简单实现

#define _CRT_SECURE_NO_WARNINGS
#include <iostream>
#include <string>
#include <vector>
#include <time.h>  
#include <windows.h>  
#include "UF.h"
using namespace std;

//用数组表示
class UF1 :public UF {
public:
	UF1(int size) {
		id = vector<int>(size);
		for (int i = 0; i < (int)id.size(); i++) {
			id[i] = i;
		}
	}
	int GetSize() {
		return id.size();
	}
	int find(int p) {
		if (p < 0 && p >= (int)id.size()) {
			return -1;
		}
		return id[p];
	}
	bool IsConnected(int p, int q) {
		return find(p) == find(q);
	}
	void UnionElements(int p, int q) {
		int pId = find(p);
		int qId = find(q);
		if (pId == qId) {
			return;
		}
		for (int i = 0; i < (int)id.size(); i++) {
			if ((int)id[i] == pId) {
				id[i] = qId;
			}
		}
	}
private:
	vector<int> id;
};
//用树表示
class UF2 :public UF
{
public:
	UF2(int size) {
		parent = vector<int>(size);
		for (int i = 0; i < (int)parent.size(); i++) {
			parent[i] = i;
		}
	}
	int GetSize() {
		return parent.size();
	}
	int find(int p) {
		if (p < 0 && p >= (int)parent.size()) {
			return -1;
		}
		while (p != parent[p]) {
			p = parent[p];
		}
		return p;
	}
	bool IsConnected(int p, int q) {
		return find(p) == find(q);
	}
	void UnionElements(int p, int q) {
		int pId = find(p);
		int qId = find(q);
		if (pId == qId) {
			return;
		}
		parent[pId] = qId;
	}

private:
	vector<int> parent;
};
//用树表示改进1
class UF3 :public UF
{
public:
	UF3(int size) {
		parent = vector<int>(size);
		sz = vector<int>(size);
		for (int i = 0; i < (int)parent.size(); i++) {
			parent[i] = i;
			sz[i] = 1;
		}
	}
	int GetSize() {
		return parent.size();
	}
	int find(int p) {
		if (p < 0 && p >= (int)parent.size()) {
			return -1;
		}
		while (p != parent[p]) {
			p = parent[p];
		}
		return p;
	}
	bool IsConnected(int p, int q) {
		return find(p) == find(q);
	}
	void UnionElements(int p, int q) {
		int pId = find(p);
		int qId = find(q);
		if (pId == qId) {
			return;
		}
		if (sz[pId] < sz[qId]) {
			parent[pId] = qId;
			sz[qId] += sz[pId];
		}
		else {
			parent[qId] = pId;
			sz[pId] += sz[qId];
		}

	}

private:
	vector<int> parent;
	vector<int> sz;
};

//用树表示改进2
class UF4 :public UF
{
public:
	UF4(int size) {
		parent = vector<int>(size);
		rank = vector<int>(size);
		for (int i = 0; i < (int)parent.size(); i++) {
			parent[i] = i;
			rank[i] = 1;
		}
	}
	int GetSize() {
		return parent.size();
	}
	int find(int p) {
		if (p < 0 && p >= (int)parent.size()) {
			return -1;
		}
		while (p != parent[p]) {
			p = parent[p];
		}
		return p;
	}
	bool IsConnected(int p, int q) {
		return find(p) == find(q);
	}
	void UnionElements(int p, int q) {
		int pId = find(p);
		int qId = find(q);
		if (pId == qId) {
			return;
		}
		if (rank[pId] < rank[qId]) {
			parent[pId] = qId;
		}
		else if (rank[qId] < rank[pId]) {
			parent[qId] = pId;
		}
		else{
			parent[qId] = pId;
			rank[pId] += 1;
		};

}
private:
	vector<int> parent;
	vector<int> rank;
};


//用树表示改进3
class UF5 :public UF
{
public:
	UF5(int size) {
		parent = vector<int>(size);
		rank = vector<int>(size);
		for (int i = 0; i < (int)parent.size(); i++) {
			parent[i] = i;
			rank[i] = 1;
		}
	}
	int GetSize() {
		return parent.size();
	}
	int find(int p) {
		if (p < 0 && p >= (int)parent.size()) {
			return -1;
		}
		while (p != parent[p]) {
			parent[p] = parent[parent[p]];
			p = parent[p];
		}
		return p;
	}
	bool IsConnected(int p, int q) {
		return find(p) == find(q);
	}
	void UnionElements(int p, int q) {
		int pId = find(p);
		int qId = find(q);
		if (pId == qId) {
			return;
		}
		if (rank[pId] < rank[qId]) {
			parent[pId] = qId;
		}
		else if (rank[qId] < rank[pId]) {
			parent[qId] = pId;
		}
		else {
			parent[qId] = pId;
			rank[pId] += 1;
		};

	}
private:
	vector<int> parent;
	vector<int> rank;
};

//用树表示改进4
class UF6 :public UF
{
public:
	UF6(int size) {
		parent = vector<int>(size);
		rank = vector<int>(size);
		for (int i = 0; i < (int)parent.size(); i++) {
			parent[i] = i;
			rank[i] = 1;
		}
	}
	int GetSize() {
		return parent.size();
	}
	int find(int p) {
		if (p < 0 && p >= (int)parent.size()) {
			return -1;
		}
		if (p != parent[p]) {
			parent[p] = find(parent[p]);
		}
		return parent[p];
	}
	bool IsConnected(int p, int q) {
		return find(p) == find(q);
	}
	void UnionElements(int p, int q) {
		int pId = find(p);
		int qId = find(q);
		if (pId == qId) {
			return;
		}
		if (rank[pId] < rank[qId]) {
			parent[pId] = qId;
		}
		else if (rank[qId] < rank[pId]) {
			parent[qId] = pId;
		}
		else {
			parent[qId] = pId;
			rank[pId] += 1;
		};

	}
private:
	vector<int> parent;
	vector<int> rank;
};



void testtime(UF*uf, int count) {
	int size = uf->GetSize();
	srand((unsigned)time(NULL));
	LARGE_INTEGER t1, t2, tc;
	QueryPerformanceFrequency(&tc);
	QueryPerformanceCounter(&t1);
	for (int i = 0; i < count; i++) {
		int a = rand() % size;
		int b = rand() % size;
		uf->UnionElements(a, b);
	}
	for (int i = 0; i < count; i++) {
		int a = rand() % size;
		int b = rand() % size;
		uf->IsConnected(a, b);
		uf->IsConnected(a, b);
	}

	QueryPerformanceCounter(&t2);
	printf("Use Time:%f\n", (t2.QuadPart - t1.QuadPart)*1.0 / tc.QuadPart);
}


int main(void)
{
	int size = 1000000;
	int count = 1000000;
/*
	UF1 myuf1 = UF1(size);
	testtime(&myuf1, count);*/

/*
	UF2 myuf2 = UF2(size);
	testtime(&myuf2, count);*/

	UF3 myuf3 = UF3(size);
	testtime(&myuf3, count);

	UF4 myuf4 = UF4(size);
	testtime(&myuf4, count);

	UF5 myuf5 = UF5(size);
	testtime(&myuf5, count);

	UF6 myuf6 = UF6(size);
	testtime(&myuf6, count);
	system("pause");
	return 0;
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值