AcWing
  • 首页
  • 活动
  • 题库
  • 竞赛
  • 应用
  • 更多
    • 题解
    • 分享
    • 商店
    • 问答
  • 吐槽
  • 登录/注册

AcWing 1145. 北极通讯网络

作者: 作者的头像   慕明 ,  2022-07-11 00:06:18 ,  所有人可见 ,  阅读 32


0


思路:按边权排序跑kruskal最小生成树,使用并查集合并时每次扩展一个结点,当未扩展的结点数为k-1的时候,说明剩下的结点可以互相通讯并且能与当前生成树通讯,此时退出循环即可
graph.png
合并完再删是错误的,如图如果有4台卫星设备,如果是删掉最大的两条边应该是1,2,3,4配置设备,但实际上是2,3,4,5配置设备

#include<iostream>
#include<string>
#include<vector>
#include<cmath>
#include<algorithm>
#include<set>
#include<stack>
#include<map>
#include<cstring>
#include<queue>
using namespace std;
const int N = 505;
int pos[N][2], p[N];
bool vis[N];
typedef long long ll;
int find(int x) {
    return x == p[x] ? x : (p[x] = find(p[x]));
}
ll getDist(int r1, int c1, int r2, int c2) {
    return (r1 - r2) * (r1 - r2) + (c1 - c2) * (c1 - c2);
}
bool cmp(vector<ll>& a, vector<ll>& b) {
    return a[2] < b[2];
}
int main()
{
    int n, k;
    cin >> n >> k;
    for (int i = 0; i < n; i++) cin >> pos[i][0] >> pos[i][1], p[i] = i;
    if(k >= n) {
        cout << "0.00";
        return 0;
    }
    vector<vector<ll>> e;
    for (int i = 0; i < n; i++) {
        for (int j = i + 1; j < n; j++) {
            e.push_back({ i, j, getDist(pos[i][0], pos[i][1], pos[j][0], pos[j][1]) });
        }
    }
    sort(e.begin(), e.end(), cmp);
    int cnt = 1;
    double ans = 0;
    for (int i = 0; i < e.size(); i++) {
        auto v = e[i];
        if (find(v[0]) != find(v[1])) {
            p[find(v[0])] = find(v[1]);
            ans = v[2];
            ++cnt;
            if(n - cnt == k - 1) {
                break;
            }
        }
    }
    ans = sqrt(ans);
    printf("%.2f", ans);
    return 0;
}

0 评论

你确定删除吗?
1024
x

© 2018-2023 AcWing 版权所有  |  京ICP备17053197号-1
用户协议  |  常见问题  |  联系我们
AcWing
请输入登录信息
更多登录方式: 微信图标 qq图标
请输入绑定的邮箱地址
请输入注册信息