Codeforces Round 977 (Div. 2)E1 Digital Village (Easy Version)(Floyd,贪心)

题目链接

Codeforces Round 977 (Div. 2)E1 Digital Village (Easy Version)

思路

首先,我们注意到 n n n的最大值只有 400 400 400。

因此,我们可以先用 F l o y d Floyd Floyd算法预处理出任意两座城市之间的最大延迟时间。

之后,我们通过在线操作,每次贪心地选出最优的一个城市,并不断更新答案。

即,我们先选出 k = 1 k=1 k=1时的最优解,之后从剩下的点里面挑出一个能够使 k = 2 k=2 k=2时最优的点,以此类推。

代码

cpp 复制代码
#include <bits/stdc++.h>
using namespace std;
#define int long long
const int N = 4e2 + 5;
const int mod = 998244353;
const int inf = 0x3f3f3f3f3f3f3f3f;
int n, m, p;
void solve()
{
	cin >> n >> m >> p;
	vector<int>city(p);
	for (int &val : city)
	{
		cin >> val;
	}
	vector<vector<int>>dist(n + 1, vector<int>(n + 1, inf));
	for (int i = 1, u, v, w; i <= m; i++)
	{
		cin >> u >> v >> w;
		dist[u][v] = min(dist[u][v], w);
		dist[v][u] = min(dist[v][u], w);
	}

	for (int i = 1; i <= n; i++)
		dist[i][i] = 0;

	for (int k = 1; k <= n; k++)
	{
		for (int i = 1; i <= n; i++)
		{
			for (int j = 1; j <= n; j++)
			{
				dist[i][j] = min(dist[i][j], max(dist[i][k], dist[k][j]));
			}
		}
	}


	vector<int>ans(n + 1);

	int sum = inf, idx = -1;
	for (auto u : city)
	{
		int res = 0;
		for (auto v : city)
		{
			res += dist[u][v];
		}
		if (sum >= res)
		{
			idx = u;
			sum = res;
			for (auto v : city)
			{
				ans[v] = dist[u][v];
			}
		}
	}

	set<int>st;
	st.insert(idx);

	cout << sum << " ";

	for (int i = 2; i <= n; i++)
	{
		if (sum == 0)
		{
			cout << sum << " ";
			continue;
		}
		int maxx = 0;
		idx = -1;
		for (auto u : city)
		{
			if (st.count(u)) continue;
			int res = 0;
			for (auto v : city)
			{
				if (st.count(v)) continue;
				if (ans[v] > dist[u][v])
				{
					res += ans[v] - dist[u][v];
				}
			}
			if (maxx <= res)
			{
				maxx = res;
				idx = u;
			}
		};
		st.insert(idx);
		sum -= maxx;
		for (auto v : city)
		{
			if (st.count(v)) continue;
			ans[v] = min(ans[v], dist[idx][v]);
		}
		cout << sum << " ";
	}
	cout << endl;
}
signed main()
{
	ios::sync_with_stdio(false);
	cin.tie(0), cout.tie(0);
	int test = 1;
	cin >> test;
	for (int i = 1; i <= test; i++)
	{
		solve();
	}
	return 0;
}
相关推荐
随意起个昵称4 小时前
区间dp-基础题目1(石子合并)
算法·动态规划
吞下星星的少年·-·4 小时前
线段树模板
算法
wunaiqiezixin4 小时前
如何在C++中创建和管理线程
c++
段一凡-华北理工大学4 小时前
2026 高炉炼铁智能化技术全景与演进路径~系列文章11:演进路径与行业未来
大数据·网络·人工智能·算法·工业智能体·高炉炼铁智能化
雪度娃娃5 小时前
转向现代C++——在意为改写的函数添加 override
开发语言·c++
王老师青少年编程5 小时前
csp信奥赛C++高频考点专项训练之前缀和&差分 --【一维差分】:[NOIP 2018 提高组] 铺设道路
c++·前缀和·差分·csp·高频考点·信奥赛·铺设道路
叶小鸡5 小时前
小鸡玩算法-力扣HOT100-多维动态规划
算法·leetcode·动态规划
星马梦缘5 小时前
aaaaa
数据结构·c++·算法
OpenApi.cc5 小时前
神经网络结构驱动+数据结构分析
数据结构·人工智能·神经网络
菜菜的顾清寒6 小时前
力扣HOT100(42)链表-随机链表的复制
算法·leetcode·链表