刚学OI114514.191980ms蒟蒻——次小生成树扎样例求助
查看原帖
刚学OI114514.191980ms蒟蒻——次小生成树扎样例求助
777131
IDNo1楼主2023/9/2 17:50
#include <bits/stdc++.h>
#define re register int
using namespace std;
int n, k;
int read()
{
    int x = 0, f = 1;
    char ch = getchar();
    while (ch < '0' || ch > '9'){if (ch == '-')f = -1;ch = getchar();}
    while (ch >= '0' && ch <= '9')x = x * 10 + ch - '0', ch = getchar();
    return x * f;
}
void write(int x)
{
    if (x < 0) {
        putchar('-');
        x = -x;
    }
    if (x > 9) {
        write(x / 10);
    }
    putchar(x % 10 + '0');
}
struct IDNo1{
	int u, v, val;
};
vector<IDNo1 > edge;
int f[1001];
int Find(re k)
{
	if(f[k] == k)
	{
		return k;
	}
	else 
	{
		return f[k] = Find(f[k]);
	}
}
int fx, fy;
void Union(re x, re y)
{
	fx = Find(x);
	fy = Find(y);
	f[fx] = fy;
}
bool cmp(IDNo1 a, IDNo1 b)
{
	return a.val < b.val;
}
vector<pair<int, int> > ban;
int main() {
	n = read(), k = read();
	for(re i = 1;i <= n;i ++)
	{
		f[i] = i;
	}
	re i, j, m;
	while(k --)
	{
		i = read(), j = read(), m = read();
		edge.push_back({i, j, m});
		edge.push_back({j, i, m});
	}
	sort(edge.begin(), edge.end(), cmp);re cnt = 0, value, now = 1e9;
	for(re i = 0;i < edge.size();i ++)
	{
		if(Find(edge[i].u) != Find(edge[i].v))
		{
			Union(edge[i].u, edge[i].v);
			ban.push_back({edge[i].u, edge[i].v});
		}
		if(cnt == n - 1)
		{
			break;
		} 
	}
	for(re k = 0;k < ban.size();k ++)
	{
		for(re i = 1;i <= n;i ++)
		{
			f[i] = 1;
		}
		cnt = value = 0;
		for(re i = 0;i < edge.size();i ++)
		{
			if((edge[i].u == ban[k].first && edge[i].v == ban[k].second) || (edge[i].v == ban[k].first && edge[i].u == ban[k].second))
			{
				continue;
			}
			if(Find(edge[i].u) != Find(edge[i].v))
			{
				Union(edge[i].u, edge[i].v);
				value += edge[i].val;
				cnt ++;
			}
			if(cnt == n - 1)
			{
				break;
			} 
		}
		now = min(value, now);
	}
	cout << now;
	return 0;
}
2023/9/2 17:50
加载中...