Luogu P8710 [蓝桥杯 2020 省 AB1] 网络分析 题解 [ 绿 ] [ 带权并查集 ]
分析
本题由于从一个节点发信息,同一个集合内的所有点都会收到信息,显然是一道要求维护各节点间关系的题,因此采用并查集的数据结构进行求解。
但由于维护关系的同时还要维护权值,所以采用带权并查集,它是一种能维护某个节点与其祖宗节点之间关系的数据结构。
带权并查集找父亲的模板如下:
int findf(int x)
{
	if(f[x]==x)return x;
	int orif=f[x];
	f[x]=findf(f[x]);
	dis[x]+=dis[orif];
	return f[x];
}
正常思路就是合并操作照常做,加上某个值就打上懒标记。
但是本题是否就这样结束了?
并不是,首先可以观察到本题要求的并不是简单的某节点和祖宗的关系,因为祖宗节点在和另一个集合合并之前,他们的储存信息是不互通的,如果仅仅就此进行合并,那么合并时某一个集合的储存信息就会平白无故地加上另一个集合在合并前的储存信息,这是不符合题意的。
而想要解决这个问题,就要将两个集合合并后分开来,即不能让一个集合祖宗的父亲,是另一个集合的祖宗。
因此,就要让他们分居不同的子树中,自然而然地就想到了虚点的解决方法。
细节实现
对于合并操作:
先找到两个集合的祖宗节点,然后创建一个虚点,使其成为这两个祖宗节点的父节点,这样就使两个集合变成了一个集合。
同时需要注意,由于合并后并没有改变两集合内任何一个节点的储存信息,所以从祖宗节点到虚点的边权为 \(0\) 。

对于发送信息操作:
依旧是先找到这个集合的祖宗节点,然后创建一个虚点,把这个虚点作为祖宗节点的父节点。
但边权方面有所不同,这个操作由于要让集合里的所有节点都接收储存信息(包括祖宗节点),因此祖宗节点到虚点的边权为储存信息的大小 \(t\) 。

当然也可以用懒标记实现,但为了使方法统一,这里加上某个值也采用虚点的方式。
输出处理
先更新一遍它到祖宗节点的距离,即它现在存储信息的大小,这样才能保证答案正确。
然后对于每个节点 \(i\) ,输出 \(dis[i]\) 即可。
由于总操作数只有 \(10^5\) ,所以最多只会有 \(10^5\) 个虚点,最坏的情况下并查集有 \(1.1*10^5\) 个节点,时间和空间复杂度都正确。
代码
#include <bits/stdc++.h>
using namespace std;
int n,m,t,f[200005],dis[200005],cnt=20000,opt,a,b;//cnt为当前要添加的虚点的编号
void init()//初始化
{
	for(int i=1;i<=200000;i++)
	{
		f[i]=i;
		dis[i]=0;
	}
}
int findf(int x)//找父节点+更新距离
{
	if(f[x]==x)return x;
	int orif=f[x];
	f[x]=findf(f[x]);
	dis[x]+=dis[orif];
	return f[x];
}
void combine(int x,int y)//合并操作
{
	int fx=findf(x),fy=findf(y);
	f[fx]=++cnt;
	f[fy]=cnt;
	dis[fx]=dis[fy]=dis[cnt]=0;
}
void add(int x,int s)//发送信息操作
{
	int fx=findf(x);
	f[fx]=++cnt;
	dis[fx]=s;
	dis[cnt]=0;
}
int main()
{
	init();
	cin>>n>>m;
	for(int i=1;i<=m;i++)
	{
		cin>>opt>>a>>b;
		if(opt==1)combine(a,b);
		else add(a,b);
	}
	for(int i=1;i<=n;i++)
	{
		findf(i);//更新距离
		cout<<dis[i]<<' ';
	}
	return 0;
}
												
											Luogu P8710 [蓝桥杯 2020 省 AB1] 网络分析 题解 [ 绿 ] [ 带权并查集 ]的更多相关文章
- Luogu P1196 [NOI2002]银河英雄传说:带权并查集
		
题目链接:https://www.luogu.org/problemnew/show/P1196 题意: 有30000个战舰队列,编号1...30000. 有30000艘战舰,编号1...30000, ...
 - luogu 1196 银河英雄传说 带权并查集
		
带权并查集,其实有点像许多队列问情况的小学奥数 #include<bits/stdc++.h> #define rep(i,x,y) for(register int i=x;i<= ...
 - luogu 2294 狡猾的商人 带权并查集
		
此题做法多啊 带权并查集,区间dp,前缀和,差分约束 1.自己写的前缀和, 11 #include<bits/stdc++.h> #define rep(i,x,y) for(regist ...
 - 第六届蓝桥杯软件类省赛题解C++/Java
		
第六届蓝桥杯软件类省赛题解C++/Java 1[C++].统计不含4的数字统计10000至99999中,不包含4的数值个数.答:暴力循环范围内所有数字判断一下就是了,答案是52488 1[Java]. ...
 - Luogu 2245 星际导航(最小生成树,最近公共祖先LCA,并查集)
		
Luogu 2245 星际导航(最小生成树,最近公共祖先LCA,并查集) Description sideman做好了回到Gliese 星球的硬件准备,但是sideman的导航系统还没有完全设计好.为 ...
 - 蓝桥杯2020.10.17B组c++
		
1.门牌制作 暴力即可 #include <iostream> #include<math.h> #include<string.h> #include<st ...
 - 蓝桥杯2020 E:七段码
		
题解 正规解法是 dfs + 并查集,首先用 dfs 将其所有的情况枚举出来,再用并查集来判断是否在一个连通块上. 许多小伙伴计算的答案为76,主要是判断连通块这方面有问题,倘若不用并查集,直接枚举一 ...
 - 第九届蓝桥杯C/C++B组题解附代码
		
1.标题:第几天 2000年的1月1日,是那一年的第1天.那么,2000年的5月4日,是那一年的第几天? 125天 打开日历就ok 2. 标题:明码 汉字的字形存在于字库中,即便在今天,16点阵的字库 ...
 - luogu P1840 Color the Axis_NOI导刊2011提高(05)|并查集
		
题目描述 在一条数轴上有N个点,分别是1-N.一开始所有的点都被染成黑色.接着我们进行M次操作,第i次操作将[Li,Ri]这些点染成白色.请输出每个操作执行后剩余黑色点的个数. 输入格式 输入一行为N ...
 - 【2020杭电多校】Total Eclipse 并查集+思维
		
题目链接:Total Eclipse 题意: t组输入,给你一个由n个点,m条边构成的图,每一个点的权值是ai.你每一次可以选择一批联通的点,然后让他们的权值都减去1.问最后把所有点的权值都变成0需要 ...
 
随机推荐
- golang之操作kafka
			
安装第三方包: go get github.com/IBM/sarama 生产者实例: package main import ( "fmt" "github.com/I ...
 - 树莓派下,打包发布能在树莓派中运行的Qt5程序和其运行环境
			
目标:把Qt程序部署到新的树莓派中. 平台:树莓派 工作:把Qt程序和运行环境分别打包 一.程序打包过程如下,仅供参考: 1.新建文件夹A,把程序拷贝到文件夹中. 2.使用ldd获取依赖关系,并复制到 ...
 - 中电金信:四川农担X中电金信大数据智能风控平台 护航金融服务乡村振兴
			
高质量金融服务是乡村振兴的重要支撑.四川省农业融资担保有限公司(以下简称"四川农担")持续探索融资担保服务,努力满足"三农"领域多样化.多层次融资担保需求的同 ...
 - Terraform Aliyun 创建ecs, kubernetes 实例
			
Terraform Aliyun 创建ecs, kubernetes 实例 terraform demo for aliyun 创建vpc, 网关, EIP, ecs, kubernetes, Ser ...
 - 【MyBatis】学习笔记13:延迟加载(懒加载)
			
目录 Mybatis13:延迟加载(懒加载) 测试 测试1 测试2 部分特殊情况处理 Mybatis13:延迟加载(懒加载) 延迟加载是分步查询的好处,默认是不开启延迟加载的,要开启需要在核心配置文件 ...
 - 2019.12.10笔记——Spring Boot热部署的使用和实现自己的热部署(类加载器相关)
			
Spring Boot热部署 热部署的使用 引入依赖 <!-- spring boot热部署的依赖 --> <dependency> <groupId>org.sp ...
 - "有邻"创始人:APP覆盖杭州千余小区 却还没认真想过赚钱的事
			
"远亲不如近邻",常被社区经济"掘金者"拿来做开场语. 在杭州,有不少互联网创业企业在深挖社区经济,例如社区O2O服务平台.杨仁斌也看中了"社区&qu ...
 - SprinfBoot报警告WARNING: An illegal reflective access operation has occurred
			
警告如图所示,该警告是因为jdk版本太高(我用的是10.0,据说9.0的也会这样),具体的原理还没有研究,它不影响项目的正常运行,但是看着很糟心有木有~~~~ 解决方案是把项目jdk降低到1.8及以下 ...
 - Visual Studio - API调试与测试工具之HTTP文件
			
后端开发,我们对于Api接口调试测试大致有以下方法:单元测试.Swagger.Postman. 但是每种方式也都有其局限性,几年前使用Visual Studio Code开发过一段时间,接触了REST ...
 - Qt Creator 5.0 发布
			
我们很高兴地宣布 Qt Creator 5.0 的发布! 正如4.15 发布博文中所宣布的,我们将切换到语义版本控制方案,因此这是 Qt Creator 很长一段时间以来的第一次主要版本更新!不过不要 ...