poj 1456 并查集优化

利用的是查并集的路径压缩思想
参考的这位大佬写的,很厉害

#include <iostream>// 优先队列 做法
#include <cstdio>
#include <queue>
#include <algorithm>

using  namespace std;

const int N = 10010;

struct E
{
	int a, b;

	bool operator < (const E w) const
	{
		return b > w.b;
	}
}ranks[N];

int main()
{
	int n;
	while (cin >> n)
	{

		int ans = 0;
		for (int i = 0; i < n; i++)
		{
			int a, b; scanf("%d %d", &a, &b);

			ranks[i] = { a, b };

			ans = max(ans, b);
		}
		priority_queue<int> q;

		sort(ranks, ranks + n);

		for (int i = 0; i < n; i++)
		{
			//cout << ranks[i].a << endl; 
		}

		int res = 0, pos = 0;
		//cout << ans << endl;
		for (int i = ans; i > 0; i--)
		{
			while (pos < n && ranks[pos].b >= i)
			{
				q.push(ranks[pos ++].a);
				//cout << ranks[pos - 1].a << endl;
			}
			if (q.size())
			{
				res += q.top();
				q.pop();
			}

			//cout << q.top() << endl;
		}
		cout << res << endl;
	}


	return 0;
}
#include <iostream>// 并查集优化版
#include <cstdio>
#include <algorithm>

using  namespace std;

const int N = 10010;

int p[N];

struct E
{
	int a, b;

	bool operator < (const E w) const
	{
		return a > w.a;
	}
	
}ranks[N];


int find(int x)
{
    int i = x, j = x;
    
    while(j != p[j]) j = p[j];
    while(i != p[x])
    {
        i = p[x], p[x] = j;
    }
    return j;
}
int main()
{
	int n;
	while (~scanf("%d", &n))
	{
        
        int ans = 0;
		for (int i = 0; i < n; i++)
		{
			int a, b; scanf("%d %d", &a, &b);
			ranks[i] = { a, b };
			
			if(b > ans)ans = b;
		}
        for(int i = 1; i <= ans; i ++) p[i] = i;
        
		sort(ranks, ranks + n);
		
		int res = 0;
		
		for(int i = 0; i < n ; i ++)
		{
		    int a = find(ranks[i].b);
		    
		    if(a != 0)  
		    {
		        res += ranks[i].a;
		        
		        p[a] = a - 1;
		    }
		}
		printf("%d\n", res);
	}


	return 0;
}
发布了53 篇原创文章 · 获赞 14 · 访问量 1895

猜你喜欢

转载自blog.csdn.net/weixin_45630535/article/details/104784963