度限制MST
POJ1639 顶点度数限制的最小生成树
做法:首先把和顶点相连的X条边全部删掉 得到顶点和 X个连通块
然后求出这X个连通块的MST 再把X条边连接回去这样我们就首先求出了X度MST
知道了X度MST 我们接下来要求X+1度MST 也就是再给顶点一条边 但是加上了这条边就会生成一个环
我们需要删掉这个环上最大权值的边
所有我们每次从N度向N+1度推进的时候需要O(N)DP求出并记录顶点到其他点的权值最大边
然后我们枚举还没有连上的边 如果删掉的边不会比加入的边大的话 就不继续推进了(剪枝)
/*Huyyt*/
//#include<bits/stdc++.h>
#include<iostream>
#include<cstdio>
#include<cstdlib>
#include<cstring>
#include<cmath>
#include<stdio.h>
#include<string.h>
#include<algorithm>
#include<map>
#include<set>
#include<vector>
#define mem(a,b) memset(a,b,sizeof(a))
#define pb push_back
using namespace std;
typedef long long ll;
typedef unsigned long long ull;
const int mod = 1e9 + ;
const int gakki = + + + + 1e9;
const int MAXN = 1e2 + , MAXM = 2e4 + ;
/*int to[MAXM << 1], nxt[MAXM << 1], Head[MAXN], ed = 1;
int cost[MAXM << 1];
inline void addedge(int u, int v, int c)
{
to[++ed] = v;
nxt[ed] = Head[u];
cost[ed] = c;
Head[u] = ed;
}*/
int dis[][];
int par[];
map<string, int> mp;
string mpu, mpv;
bool connect[];
int n, K;
int cnt = , root, costnow, ans = , ccnt = ;
int dp[];
struct node
{
int u, v, c;
} edge[], cmin[], rootedge[], cur, choose[];
bool cmp(node a, node b)
{
return a.c < b.c;
}
int findpar(int x)
{
return par[x] == x ? x : par[x] = findpar(par[x]);
}
void init()
{
for (int i = ; i <= n; i++)
{
dp[i] = -;
choose[i].c = -;
}
}
void dfs(int x, int pre)
{
node better;
for (int v = ; v <= n; v++)
{
if (v != pre && (dis[x][v] != ))
{
if (dis[x][v] > choose[x].c)
{
choose[v].u = x, choose[v].v = v, choose[v].c = dis[x][v];
dp[v] = dis[x][v];
}
else
{
choose[v] = choose[x];
dp[v] = dp[x];
}
dfs(v, x);
}
}
}
int main()
{
scanf("%d", &n);
for (int i = ; i <= n + ; i++)
{
par[i] = i;
cmin[i].c = ;
for (int j = ; j <= n + ; j++)
{
dis[i][j] = ;
}
}
mp["Park"] = ;
for (int i = ; i <= n; i++)
{
cin >> mpu >> mpv >> costnow;
if (!mp[mpu])
{
mp[mpu] = ++cnt;
}
if (!mp[mpv])
{
mp[mpv] = ++cnt;
}
edge[i].u = mp[mpu], edge[i].v = mp[mpv];
edge[i].c = costnow;
//cout << edge[i].u << " " << edge[i].v << " " << costnow << endl;
if (edge[i].u == || edge[i].v == )
{
rootedge[++ccnt] = edge[i];
}
}
scanf("%d", &K);
sort(edge + , edge + + n, cmp);
for (int i = ; i <= n; i++)
{
int u1, v1;
u1 = edge[i].u, v1 = edge[i].v;
if (u1 != && v1 != )
{
int fx = findpar(u1), fy = findpar(v1);
if (fx != fy)
{
par[fx] = fy;
dis[u1][v1] = dis[v1][u1] = edge[i].c;
ans += edge[i].c;
//cout << " u " << u1 << " v " << v1 << " " << ans << endl;
}
}
}
for (int i = ; i <= ccnt; i++)
{
int u1, v1;
u1 = rootedge[i].u, v1 = rootedge[i].v;
if (u1 != )
{
int fx = findpar(u1);
if (cmin[fx].c > rootedge[i].c)
{
cmin[fx] = rootedge[i];
}
}
else
{
int fx = findpar(v1);
if (cmin[fx].c > rootedge[i].c)
{
cmin[fx] = rootedge[i];
}
}
}
int m = ;
for (int i = ; i <= cnt; i++)
{
int fx = findpar(i);
if (!connect[fx])
{
m++;
connect[fx] = true;
cur = cmin[fx];
dis[cur.u][cur.v] = dis[cur.v][cur.u] = cur.c;
ans += cur.c;
//cout << " i " << i << " u " << cur.u << " v " << cur.v << " " << ans << endl;
for (int j = ; j <= ccnt; j++)
{
if (rootedge[j].u == cur.u && rootedge[j].v == cur.v)
{
rootedge[j].c = -;
break;
}
}
}
}
for (int i = m + ; i <= K; i++)
{
init();
dfs(, -);
int ansmanx = ;
node best;
int want;
int where;
for (int j = ; j <= ccnt; j++)
{
if (rootedge[j].c != -)
{
int u1, v1;
u1 = rootedge[j].u, v1 = rootedge[j].v;
if (u1 != )
{
if (dp[u1] - rootedge[j].c > ansmanx)
{
where = j;
best = rootedge[j];
want = u1;
ansmanx = dp[u1] - rootedge[j].c;
}
}
else
{
if (dp[v1] - rootedge[j].c > ansmanx)
{
where = j;
best = rootedge[j];
want = v1;
ansmanx = dp[v1] - rootedge[j].c;
}
}
}
}
if (ansmanx == )
{
break;
}
dis[best.u][best.v] = dis[best.v][best.u] = best.c;
dis[choose[want].u][choose[want].v] = dis[choose[want].v][choose[want].u] = ;
rootedge[where].c = -;
ans -= ansmanx;
}
printf("Total miles driven: %d\n", ans);
//cout << "Total miles driven: " << ans << endl;
return ;
}
//度生成树
度限制MST的更多相关文章
- poj 1639 Picnic Planning 度限制mst
https://vjudge.net/problem/POJ-1639 题意: 有一群人,他们要去某一个地方,每个车可以装无数个人,给出了n条路,包含的信息有路连接的地方,以及路的长度,路是双向的,但 ...
- K度限制MST poj 1639
/* k度限制MST:有一个点的度<=k的MST poj 1639 要求1号点的度不超过k 求MST 我们先把1号点扔掉 跑MST 假设有sum个连通分支 然后把这sum个分支连到1上 就得到了 ...
- CF-125E MST Company (单度限制最小生成树)
参考红宝书 题目链接 对除 1 号点顶点外的点集,求一次最小生成森林,对于最小生成森林的联通分量,选择最短的一条边与 1 号点相连.设此时 1 号点的度为 \(k_0\),如果 \(k_0\lt L\ ...
- 基于MST的立体匹配及相关改进(A Non-Local Cost Aggregation Method for Stereo Matching)
怀着很纠结的心情来总结这篇论文,这主要是因为作者提虽然供了源代码,但是我并没有仔细去深究他的code,只是把他的算法加进了自己的项目.希望以后有时间能把MST这一结构自己编程实现!! 论文题目是基于非 ...
- 2015baidu复赛2 连接的管道(mst && 优先队列prim)
连接的管道 Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)Total Submi ...
- Educational Codeforces Round 3 E. Minimum spanning tree for each edge LCA/(树链剖分+数据结构) + MST
E. Minimum spanning tree for each edge Connected undirected weighted graph without self-loops and ...
- POJ 3241 Object Clustering(Manhattan MST)
题目链接:http://poj.org/problem?id=3241 Description We have N (N ≤ 10000) objects, and wish to classify ...
- UVA 11354 Bond 邦德 (RMQ,最小瓶颈MST)
题意: n个城市,m条路,每条路有个危险值,要使得从s走到t的危险值最小.回答q个询问,每个询问有s和t,要求输出从s到t最小的危险值.(5万个点,10万条边) 思路: 其实要求的是任意点对之间的最小 ...
- UVA 1151 Buy or Build (MST最小生成树,kruscal,变形)
题意: 要使n个点之间能够互通,要使两点直接互通需要耗费它们之间的欧几里得距离的平方大小的花费,这说明每两个点都可以使其互通.接着有q个套餐可以选,一旦选了这些套餐,他们所包含的点自动就连起来了,所需 ...
随机推荐
- Introduction to pointers in C
The basic purpose of developing a C programming tutorial for this website – CircuitsToday – is to ma ...
- Data - 【转】数据统计、数据挖掘、大数据、OLAP的区别
原文链接 数据分析 数据分析是一个大的概念,理论上任何对数据进行计算.处理从而得出一些有意义的结论的过程,都叫数据分析. 从数据本身的复杂程度.以及对数据进行处理的复杂度和深度来看,可以把数据分析分为 ...
- list 属性字段直接转成字符串数组
List<Car> cars = //whatever; string concat = String.Join(",", cars.Select(c => c. ...
- idea关闭自动更新
如何关闭idea的自动更新? File-Setting-Appearance&Beha-System Setting-Updates 取消勾选Automatically check updat ...
- SVN(linux版)安装与使用
SVN(linux版)安装与使用 一 简述: SVN有2种运行方式,一种是 linux自带的轻量级服务器svnserve,一种是基于Apache的. 基于svnserve的,默认端口为3690,通过 ...
- Durable NAND flash memory management
词条积累 1.NAND flash memory http://www.searchstorage.com.cn/whatis/word_6052.htm http://baike.baidu.com ...
- netcore发布的坑
当我选择目标运行时为Linux-64时,生成的接口为第二图, 而当我选择目标运行时为可移植或windows-64时,生成的接口则是正确的.和我写的代码,以及本地按F5启动调试的效果一致. 整个项目从v ...
- 利用commons-pool2自定义对象池
一.为什么使用对象池 恰当地使用对象池化技术,可以有效地减少对象生成和初始化时的消耗,提高系统的运行效率.commons-pool2是Apache下一个开源的公共资源池.我们可以根据它来快速的建立 ...
- 【pytorch】学习笔记(四)-搭建神经网络进行关系拟合
[pytorch学习笔记]-搭建神经网络进行关系拟合 学习自莫烦python 目标 1.创建一些围绕y=x^2+噪声这个函数的散点 2.用神经网络模型来建立一个可以代表他们关系的线条 建立数据集 im ...
- Django基础之模型(models)层(上)
目录 Django基础之模型(models)层 单表查询 必知必会13条 神奇的双下划线查询 多表查询 外键的字段的增删改查 表与表之间的关联查询 基于双下划线的跨表查询(连表查询) 补充知识 Dja ...