并查集进阶——带权并查集

带权并查集是在并查集的基础上加入数组来记录某些值,比如说当前家族的人数
原理也较简单,直接在合并时相加赋值就可以了,但是不要忘记初始化

例题一.合并家族

给定一个数n,代表总人数,一开始每个人自己是一家,给定另一个数m,代表操作总次数,每次操作可以有三种方式:

1、输入“C”和两个数,代表把这两个数合并到一个家族中
2、输入“Q1”和两个数,代表询问这两个数是否在同一家族中
3、输入“Q2”和一个数,代表询问这个数所在的家族的总人数

这个题需要在普通并查集的基础上加入一个数组 d i s i dis_i disi 来记录家族的人的个数,初始化时需要把每一个家族的人数归一,合并时,家族的人数也要相加赋值

#include<bits/stdc++.h>
using namespace std;
int fa[100005],dis[100005],n,m;
int Find(int x){if(fa[x]==x){return x;}int xx=Find(fa[x]);return fa[x]=xx;
}
void Union(int x,int y){x=Find(x);y=Find(y);if(x!=y){fa[x]=y;dis[y]+=dis[x];}
}
void Init(){for(int i=1;i<=n;i++){dis[i]=1;fa[i]=i;}
}
int main(){scanf("%d%d",&n,&m);Init();for(int i=1;i<=m;i++){char s[5];scanf("%s",s);if(s[0]=='C'){int xx,yy;scanf("%d%d",&xx,&yy);Union(xx,yy);}else if(s[1]=='1'){int xx,yy;scanf("%d%d",&xx,&yy);if(Find(xx)==Find(yy)){printf("Yes\n");}else{printf("No\n");}}else{int xx;scanf("%d",&xx);printf("%d\n",dis[Find(xx)]);}}return 0;
}

例题二.信息传递

P2661 [NOIP2015 提高组] 信息传递
给定n个同学,每个同学都会告诉一个同学自己的信息,问进行几轮传递后这位同学能够收到自己的信息

每次传递都会耗费一轮,所以这里的dis是用来存储耗费的轮数,初始化为0,每次合并时把轮数加一,直到出现需合并的两数的祖先是同一人,这就说明出现环了,比较记录最小值

#include<bits/stdc++.h>
using namespace std;
int fa[1000005],dis[1000005],minn,n,t;int Find(int x){if(fa[x]==x){return x;}int root=Find(fa[x]);dis[x]+=dis[fa[x]];return fa[x]=root;
}
void Union(int x,int y){int xx=Find(x);int yy=Find(y);if(xx==yy){minn=min(minn,dis[x]+dis[y]+1);return ;}fa[xx]=yy;dis[x]=dis[y]+1;
}
void Init(){for(int i=0;i<=n;i++){fa[i]=i;dis[i]=0; }
}
int main(){scanf("%d",&n);Init();minn=0x3f3f3f3f;for(int i=1;i<=n;i++){scanf("%d",&t);Union(i,t);}printf("%d",minn);return 0;
}

例题三.堆箱子

给定n和m分别代表箱子的总个数和操作的次数

每次操作有两种:
1、输入“M”和两个数,代表把第一个数所在的那一堆箱子放到第二个数所在的那堆箱子的上面
2、输入“C”和一个数,代表询问那个数所代表的那个箱子的下面有多少个箱子

这道题不仅需要点权,还需要边权,点权记录箱子的个数,边权记录该箱子之下箱子的个数,在合并的过程中,将边权赋值给点权,边权相加

边权初始化为1,点权初始化为0

#include<bits/stdc++.h>
using namespace std;
int fa[1000005],dis[1000005],num[1000005],n,m;
int Find(int x){if(fa[x]==x){return x;}int root=Find(fa[x]);dis[x]+=dis[fa[x]];return fa[x]=root;
}
void Union(int x,int y){int xx=Find(x);int yy=Find(y);if(xx==yy){return ;}dis[xx]=num[yy];num[yy]+=num[xx];fa[xx]=yy;
}
void Init(){for(int i=0;i<=n;i++){fa[i]=i;num[i]=1;dis[i]=0; }
}
int main(){scanf("%d%d",&n,&m);Init();for(int i=1;i<=m;i++){char s[5];scanf("%s",s);if(s[0]=='M'){int x1,y1;scanf("%d%d",&x1,&y1);Union(x1,y1);}else{int x1;scanf("%d",&x1);int y1=Find(x1);printf("%d\n",dis[x1]);}}return 0;
}

种类并查集

种类并查集可以维护对立的关系,例如:敌人的敌人是朋友

例题四.食物链

P2024 [NOI2001] 食物链

输入n,k分别代表动物的总个数和话的个数
每句话有两种形式:
1、输入“1”和两个数,代表这两个数是同类
2、输入“2”和两个数,代表第一个动物吃第二个动物

要求判断给定的话里面有多少是假话

假话有那么几种情况:1、数字比n大 2、违背了之前所说的关系 3、自己吃自己

此题需要开一个3倍大小的 f a fa fa ,一倍下标存本身,二倍下标存猎物,三倍下标存天敌
输入1时,二者本身、二者猎物、二者天敌都是同类,把他们合并起来
输入2时,X是Y的天敌,所以Y的天敌和X是同类,把X和2n+Y合并起来,X的猎物也应该和Y是同类,所以把X+n和Y合并起来,还有题目中强调的“食物链呈环形:A吃B,B吃C,C吃A”,所以X的天敌应是Y的猎物,把X+2n和Y+n合并在一块

每次操作前应该判断是否合规,如果不合规,ans++,continue,不正确的情况不操作

#include<bits/stdc++.h>
using namespace std;
int fa[300005],n,m,ans;
int Find(int x){if(fa[x]==x){return x;}return fa[x]=Find(fa[x]);
}
void Union(int x,int y){int xx=Find(x);int yy=Find(y);if(xx==yy){return ;}fa[xx]=yy;
}
void Init(){for(int i=1;i<=3*n;i++){fa[i]=i;}
}
int main(){scanf("%d%d",&n,&m);Init();for(int i=1;i<=m;i++){int tt;scanf("%d",&tt);int xx,yy;scanf("%d%d",&xx,&yy);if(tt==1){if(xx>n||yy>n||Find(xx+n)==Find(yy)||Find(xx+2*n)==Find(yy)){ans++;continue;}Union(xx,yy);Union(xx+n,yy+n);Union(xx+2*n,yy+2*n);}else{if(Find(xx)==Find(yy)||Find(xx+2*n)==Find(yy)||xx==yy||xx>n||yy>n){ans++;continue;}Union(xx,yy+2*n);Union(xx+n,yy);Union(xx+2*n,yy+n);}}printf("%d\n",ans);return 0;
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/782725.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

二维码门楼牌管理应用平台建设:引领现代化小区管理新篇章

文章目录 前言一、二维码门楼牌管理应用平台概述二、三维动态单体化技术的优势三、二维码门楼牌管理应用平台的应用场景四、展望未来 前言 随着城市化的快速推进&#xff0c;现代化小区如雨后春笋般涌现&#xff0c;对小区管理的效率和智能化提出了更高要求。二维码门楼牌管理…

代码随想录Day39

Day 39 动态规划 part02 今日任务 62.不同路径 不同路径 II 代码实现 62.不同路径 public int uniquePaths(int m, int n) {if (m < 1 || n< 1) return 1;int[][] dp new int[m][n];for (int i 0; i < dp.length; i) {for (int j 0; j < dp[i].length; j) …

鸿蒙OS开发实例:【瀑布流式图片浏览】

介绍 瀑布流式展示图片文字&#xff0c;在当前产品设计中已非常常见&#xff0c;本篇将介绍关于WaterFlow的图片浏览场景&#xff0c;顺便集成Video控件&#xff0c;以提高实践的趣味性 准备 请参照[官方指导]&#xff0c;创建一个Demo工程&#xff0c;选择Stage模型熟读Har…

【算法】基数排序

简介 基数排序&#xff08;*Radix sort&#xff09;是一种非比较排序算法&#xff08;non-comparative sorting algorithm&#xff09;。现代计算机的基数排序算法由 计数排序 算法的开发人哈罗德H西华德&#xff08;Harold H. Seward&#xff09;于1954年于麻省理工大学开发。…

智能换气系统的设计与实现

智能换气系统的设计与实现 摘要&#xff1a; 随着现代家居对室内空气质量要求的日益提高&#xff0c;智能换气系统成为了确保室内环境舒适与健康的关键技术。本文详细探讨了智能换气系统的设计与实现过程&#xff0c;该系统结合了传感器技术、微控制器技术和智能控制算法&…

vue.router和vue.route

Vue Router 和 Vue Route 是 Vue.js 中用于构建单页面应用&#xff08;SPA&#xff09;路由系统的两个核心概念。Vue Router 是 Vue.js 的官方路由管理器&#xff0c;而 Vue Route 则是在 Vue 组件内部通过 $route 对象来访问当前路由的信息。 Vue Router 的使用 Vue Router …

图像分割论文阅读:Automatic Polyp Segmentation via Multi-scale Subtraction Network

这篇论文的主要内容是介绍了一种名为多尺度差值网络&#xff08;MSNet&#xff09;的自动息肉分割方法。 1&#xff0c;模型整体结构 整体结构包括编码器&#xff0c;解码器&#xff0c;编码器和解码器之间是多尺度差值模块模块&#xff08;MSM&#xff09;&#xff0c;以及一…

【前端】-

相对路径和绝对路径是描述文件位置的两种方式。 1. 相对路径&#xff1a;相对于自己的目标文件的位置&#xff0c;以引用文件之间网页所在位置为参考基础&#xff0c;而建立出的目录路径。因此&#xff0c;当保存于不同目录的网页引用同一个文件时&#xff0c;所使用的路径将不…

带头双向循环链表的实现及注释教学

首先需要借助三个文件 test.c list.h list.c 目录 list.h list.c test.c list.h 用于声明函数及创建结构体、包含头文件 #pragma once #include<stdio.h> #include<stdlib.h> #include<assert.h> #include<stdbool.h>typedef int LTDa…

LeetCode 2908. 元素和最小的山形三元组 I。(通过JavaScript实现)

给你一个下标从 0 开始的整数数组 nums 。 如果下标三元组 (i, j, k) 满足下述全部条件&#xff0c;则认为它是一个 山形三元组 &#xff1a; i < j < knums[i] < nums[j] 且 nums[k] < nums[j] 请你找出 nums 中 元素和最小 的山形三元组&#xff0c;并返回其 …

Vue3 使用 v-bind 动态绑定 CSS 样式

在 Vue3 中&#xff0c;可以通过 v-bind 动态绑定 CSS 样式。 语法格式&#xff1a; color: v-bind(数据); 基础使用&#xff1a; <template><h3 class"title">我是父组件</h3><button click"state !state">按钮</button>…

STL容器vector

vector存放基本数据类型 STL中最常用的容器就是vector&#xff0c;可以理解成为数组。 需要掌握如何向vector容器插入数据、遍历vector。 #include <iostream> #include <Windows.h> #include <vector> #include <algorithm> // 使用STL提供的遍历算法…

牛客NC31 第一个只出现一次的字符【simple map Java,Go,PHP】

题目 题目链接&#xff1a; https://www.nowcoder.com/practice/1c82e8cf713b4bbeb2a5b31cf5b0417c 核心 Map参考答案Java import java.util.*;public class Solution {/*** 代码中的类名、方法名、参数名已经指定&#xff0c;请勿修改&#xff0c;直接返回方法规定的值即可*…

INA350ABSIDDFR 仪表放大器 单路低功耗 TSOT-23-8

NA350ABSIDDFR 是一款高精度、低功耗、单片式精密运算放大器。它具有出色的直流精度和低失调电压&#xff0c;适用于需要高精度信号处理的应用。这款产品广泛应用于各种领域&#xff0c;如工业控制、医疗设备、测试与测量设备以及通信系统等。 制造商: Texas Instruments …

思维题,LeetCode331. 验证二叉树的前序序列化

一、题目 1、题目描述 序列化二叉树的一种方法是使用 前序遍历 。当我们遇到一个非空节点时&#xff0c;我们可以记录下这个节点的值。如果它是一个空节点&#xff0c;我们可以使用一个标记值记录&#xff0c;例如 #。 例如&#xff0c;上面的二叉树可以被序列化为字符串 &quo…

3.恒定乘积自动做市商算法及代码

中心化交易所的安全风险 在中心化交易所中注册账户时&#xff0c;是由交易所生成一个地址&#xff0c;用户可以向地址充币&#xff0c;充到地址之后交易所就会根据用户充币的数量显示在管理界面中。但是充币的地址是掌管在交易所之中的&#xff0c;资产的控制权还是在交易所。…

[数据集][目标检测]公共场所危险物品检测数据集VOC+YOLO格式1431张6类别

数据集格式&#xff1a;Pascal VOC格式YOLO格式(不包含分割路径的txt文件&#xff0c;仅仅包含jpg图片以及对应的VOC格式xml文件和yolo格式txt文件) 图片数量(jpg文件个数)&#xff1a;1431 标注数量(xml文件个数)&#xff1a;1431 标注数量(txt文件个数)&#xff1a;1431 标注…

从0开始搭建基于VUE的前端项目(二) 安装和配置element-ui组件库

版本和地址 ElementUI 2.15.14 (https://element.eleme.io/)按需引入的插件 babel-plugin-component(1.1.1) https://github.com/ElementUI/babel-plugin-component安装 npm install element-ui完整引入(不建议) 这种方式最后打包的源文件很大,造成网络资源的浪费main.jsimpo…

dubbo的分布式事务原理、Java如何实现dubbo的分布式事务

1、dubbo的分布式事务原理 Dubbo支持分布式事务的原理主要有两种方式&#xff1a;基于本地消息表和基于可靠消息服务。 1、基于本地消息表 1.Dubbo在服务提供者和消费者之间插入一个本地消息表来记录事务消息。 2.在调用远程服务前&#xff0c;Dubbo会将事务消息插入到本地消…

MFC(二)集成基础控件

目录 OnCreateCStatic【标签&#xff0c;图片】CEdit【文本框&#xff0c;密码框&#xff0c;数值框&#xff0c;文本区】CButton【按钮&#xff0c;单选按钮&#xff0c;多选按钮】CComboBox【下拉列表&#xff0c;列表】CSliderCtrl【滑动条】CListCtrl【表格】CAnimateCtrl【…