首页 > 其他分享 >P1967 [NOIP2013 提高组] 货车运输

P1967 [NOIP2013 提高组] 货车运输

时间:2023-09-24 21:25:06浏览次数:41  
标签:cnt NOIP2013 min int 货车运输 ww ff ans P1967

P1967 [NOIP2013 提高组] 货车运输

因为可能成环,这样可能导致到达点的最小权值不一,所以用最小生成树的方法重新建图
然后我是利用倍增的思想建立从i点开始,到上面点的距离ff和最小权值ww
因为最小权值不好直接建立,所以不如最后统一建立
最后就是寻找最近公共祖先的模板了
一组hack:
cin
5 4
1 2 1
1 3 1
2 3 1
4 5 5
1
4 5
cout
5
注意这组数据,也就是说数据可能是森林,要遍历完所以数据,当时跳进坑了。

点击查看代码
#include<bits/stdc++.h>
using namespace std;
const int N = 5e5 + 10;
int n, m;
//链式前向星
int h[N], ne[N * 2], w[N * 2], to[N * 2],cnt;
void add(int a, int b,int c) {
	to[++cnt] = b;
	ne[cnt] = h[a];
	w[cnt] = c;
	h[a] = cnt;
}
//Kruskal最小生成树,改为最大
struct edge {
	int u, v, w;
	bool operator<(const edge& a)const {
		return w>a.w;
	}
}e[N];
int f[N];
int find(int x) {
	return f[x] == x ? x : f[x] = find(f[x]);
}
void Kruskal() {
	sort(e + 1, e + 1 + m);
	for (int i = 1; i <= n; i++) f[i] =i;
	for (int i = 1; i <= m; i++) {
		int x = find(e[i].u);
		int y = find(e[i].v);
		if (x != y) {
			f[x] = y;
			add(e[i].u, e[i].v, e[i].w);
			add(e[i].v, e[i].u, e[i].w);
		}
	}
}
//先遍历一遍,找好跳一个点的距离和权值
int ff[N][22], ww[N][22],dep[N],vis[N];
void dfs(int u, int father) {
	vis[u] = 1;
	dep[u] = dep[father] + 1;
	ff[u][0] = father;
	for (int i = h[u]; i; i = ne[i]) {
		int v = to[i];
		if (v == father) continue;
		ww[v][0] = w[i];
		dfs(v, u);
	}
}
//最近公共祖先模板
int lca(int u, int v) {
	if (find(u) != find(v)) return -1;
	if (dep[u] < dep[v]) swap(u, v);
	int ans = 1e9;//初始化无穷
	for (int i = 19; i >= 0; i--) {
		if (dep[ff[u][i]]>= dep[v]) {
			ans = min(ans, ww[u][i]);//维护最小
			u = ff[u][i];
		}
	}
	if (v == u) return ans;//相遇直接返回
	for (int i = 19; i >= 0; i--) {
		if (ff[u][i] != ff[v][i]) {
			ans = min(ans, min(ww[u][i], ww[v][i]));//维护最小
			u = ff[u][i]; v = ff[v][i];
		}
	}
	return min(ans, min(ww[u][0], ww[v][0]));//维护最小
}

int main() {
	cin >> n >> m;
	for (int i = 1; i <= m; i++) {
		int x, y, z;
		cin >> x >> y >> z;
		e[i] = { x,y,z };
	}
	Kruskal();
	for (int i = 1; i <= n; i++) {//全部遍历
		if (!vis[i]) {
			dfs(i, 0);
		}
	}
	for (int i = 1; i <= 19; i++) {//统一计算
		for (int j = 1; j <= n; j++) {
			ff[j][i] = ff[ff[j][i - 1]][i - 1];
			ww[j][i] = min(ww[ff[j][i - 1]][i - 1], ww[j][i - 1]);
		}
	}
	int q;
	cin >> q;
	while (q--) {
		int x, y;
		cin >> x >> y;
		cout << lca(x, y) << '\n';
	}
}

标签:cnt,NOIP2013,min,int,货车运输,ww,ff,ans,P1967
From: https://www.cnblogs.com/bu-fan/p/17726687.html

相关文章

  • NOIP2013提高组复赛day1解析
    1.错误原因:想的太复杂正解:10^k轮,会使x号小伙伴变到(x+m*10^k)%n号,直接套用公式代码:#include<bits/stdc++.h>#definelllonglongusingnamespacestd;lln,m,k,x;llquickPow(lla,llb,llmod){ llans=1; while(b){ if(b&1)ans=((ans%mod)*(a%mod))%mod; a=((......
  • NOIP2013提高组初赛易错题解析
    7. 正解:可以画出递归树,画出后应该是这样子的 画出递归树,就可以得出答案时间复杂度为O(Fn) 15. 正解:2T(n/2)=O(logn)T(n)=2*T(n/2)+2*n=O(nlogn)三.2. 错误原因:蒙的正解:通过观察,可以找到递推关系式,f[n]=1/n*(n+f[1]+f[2]+...+f[n]),f[1]=0,f[2]=2,经过计算......
  • 「NOIP2013」货车运输 题解
    「NOIP2013」货车运输前言这道题算是一个稍有思维难度的MST+LCA题目了。稍微卡了一会(0-88-88-88-100(打表)-100(打表)-100(正解)),开始是打了表过了,后面在DCZ的帮助下正解通过(下面注释提到的一个坑)。题目大意给出一张无向图\(G\),有\(n\)个点和\(m\)个边\((x,y)=z\),找到一......
  • NOIP2013-2023题解
    本文章主要是为了不想卷题的时候不是特别颓废而准备本文章是为了总结NOIP最近的题目(为了今年NOIP做准备),目前还没写完,尽量做的全面一些。2013积木大赛给定一个长度为\(n\)的序列\(h_i\),初始有一个全为\(0\)的序列,每次操作可以任意选择\(L,R\),使得\([L,R]\)这段区......
  • NC16527 [NOIP2013]货车运输
    题目链接题目题目描述A国有n座城市,编号从1到n,城市之间有m条双向道路。每一条道路对车辆都有重量限制,简称限重。现在有q辆货车在运输货物,司机们想知道每辆车在不超过车辆限重的情况下,最多能运多重的货物。输入描述第一行有两个用一个空格隔开的整数n,m,表示A国......
  • 【题解】Luogu[P1967] NOIP2013 提高组 货车运输
    Link→很容易想到一个暴力做法,就是跑一遍Floyd,\(F_{i,j}\)表示\(i\)到\(j\)最大载重量,转移\(F_{i,j}=\max\{F_{i,j},\min\{F_{i,k},F_{k,j}\}\}\)。显然时间复杂度\(O(n^3)\)是过不了的。我们发现,因为是求两点路径中使得最小值最大,实际上有一些较小的路径是不会走......
  • [NOIP2013 普及组] 表达式求值
    [NOIP2013普及组]表达式求值题目描述给定一个只包含加法和乘法的算术表达式,请你编程计算表达式的值。输入格式一行,为需要你计算的表达式,表达式中只包含数字、加法运算符“\(+\)”和乘法运算符“$\times$”,且没有括号,所有参与运算的数字均为\(0\)到\(2^{31}-1\)之......
  • 洛谷 P1967 货车运输
    P1967NOIP2013提高组]货车运输-洛谷|计算机科学教育新生态(luogu.com.cn)这个题目算是lca的稍微拓展吧。主要思考方向应该是很明显的。就是考虑一条路径上权值最......
  • P1983 [NOIP2013 普及组] 车站分级
    P1983[NOIP2013普及组]车站分级https://www.luogu.com.cn/problem/P1983 思路https://www.cnblogs.com/tomori/p/14331510.html   Codehttps://www.luo......
  • m基于ACO蚁群优化的货车运输路线规划matlab仿真,考虑车辆载重,单位运输成本等因素
    1.算法描述蚁群算法是通过对自然界中真实蚂蚁的集体行为的观察,模拟而得到一种仿生优化算法,它具有很好的并行性,分布性.根据蚂蚁群体不同的集体行为特征,蚁群算法可分为受......