首页 > 其他分享 >强连通分量

强连通分量

时间:2024-04-25 13:13:17浏览次数:17  
标签:连通 top st dfn low 节点 分量

定义:

强连通指的是对于一个有向图,每个点都有路径到另外一个点。

强连通分量则指的是对于一个图,它的极大强连通子图。

tanjan 求法:

对于一个图,考虑他的 dfs 生成树(即为对原图进行 dfs 的一棵树)。

那么对于这棵树,搜索时会出现四种边:

树枝边:搜索到没被访问过的节点,且在树中当前节点的直接儿子

前向边:搜索到没被访问的节点,但在树中当前节点的间接儿子

横叉边:搜索到已访问到的节点,但不是当前节点的祖先

返祖边:搜索到已访问的节点,且当前节点的祖先


性质: 如果 \(u\) 是一个强连通分量中的第一个访问到的节点,那么其余节点一定是在搜索树中 \(u\) 的子树中。

证明: 反证法即可。


那么现在我们考虑到达 \(u\) 节点的时间戳,即为 \(u\) 是第几个到达的。这里记作 \(dfn[u]\).

在回溯的过程中,维护一个栈,用于存储待处理的节点。

再考虑在以 \(u\) 为根的子树中能到达的最早的在栈中的节点的时间戳。这里记作 \(low[i]\).

那么对于没被访问的节点,有 \(low[u]=\min(low[u],low[v])\)

对于访问过的且在栈中的节点,有 \(low[u]=\min(low[u],dfn[v])\)

其他情况对 \(low[u]\) 均无贡献。

那么当 \(low[u]=dfn[u]\) 时,就表示所有在以 \(u\) 为根的子树中 \(low\) 值等于 \(low[u]\) 的节点组成的图已经满足了极大性和强连通性

且因为以 \(u\) 为根的子树中 \(low\) 值不等于 \(low[u]\) 的节点已经处理完了,所以这个栈中在 \(u\) 上的节点的 \(low\) 值都等于 \(low[u]\) ,此时他们就组成了一个强连通分量

代码:

void tarjan(int u){
	dfn[u]=low[u]=++dfnnow;
	vis[u]=true;
	st[++top]=u;
	in_st[u]=true;
	for(int i=head[u];i;i=edges[i].next){
		int v=edges[i].v;
		if(!vis[v]){
			tarjan(v);
			low[u]=min(low[u],low[v]);
		}
		else if(in_st[v]){
			low[u]=min(low[u],dfn[v]);
		}
	}
	if(dfn[u]==low[u]){
		scc++;
		while(st[top]!=u){
			siz[scc]++;
			in_st[st[top]]=false;
			col[st[top]]=scc;
			top--;
		}
		siz[scc]++;
		in_st[st[top]]=false;
		col[st[top]]=scc;
		top--;
	}
	return;
}

标签:连通,top,st,dfn,low,节点,分量
From: https://www.cnblogs.com/little-corn/p/18157430

相关文章

  • 图的连通性(tarjan) 学习笔记
    本文可能含有:部分代码省略,部分资源来源于网络,极其模糊不清的语言表述,粗浅到浮于言表的对于此算法的认识。本文仅用于个人学习与报告使用。若有侵权,请洛谷私信联系笔者要求删除。就连上述文字都是抄袭大佬@GClock_519的,可以看得出笔者拙劣的语文水平(图的连通性相关,顾名思义,......
  • 桥、割点和边双连通分量
    桥定义:删除后会增加联通块数量的边被称作桥。那么,如何求解呢?方法一首先跑出一颗dfs树。比如下图(\(2-6,1-5\)的边是非树边):可以发现,所有非树边和其构成的环上的所有边不可能是桥,因为删去后仍可以通过环的另一半。比如上图中只有\(1-2\)一个桥。那是不是除了这些边以外都是......
  • 强连通分量、缩点
    强连通分量定义:强连通分量是指一个任意两点都可互相到达的极大子图。求解思路和桥、割点和边双连通分量很类似。首先跑出一颗dfs树,令\(dfn_u\)表示\(u\)的时间戳,\(low_u\)表示\(u\)的子树中仅通过非树边能到达的\(\min\{dfn_v\}\)。比如下图:在这张图中,黑色边为树边......
  • Tarjan 求双连通分量(点双连通分量、边双连通分量)
    注意:本文只针对无向图。对于无向图,显然不能只考虑简单的连通关系,应该研究一些更强的连通关系:双连通。前置芝士点双连通分量:若一个连通分量任意两点间都存在至少两条不经过(除起点和终点外)相同点的路径,我们就称这个连通分量为点双连通分量。边双连通分量:同理,若一个连通分量......
  • 连通性+ 1
    早在普及组的时候,我们就学会了:DFS(BFS)搜连通块并查集在加边的情况下动态维护连通块(支持离线处理删边)现在,我问你:我删去一个点/边,判断剩下的图存在原本某两个连通的点现在不连通?我随机删去一条边,判断剩下的图中某两个点是否一定连通?我随机给你一些点,判断其中两两是......
  • 边双连通分量
    边双连通分量我们令双连通表示两个节点之间段开一条边还是连通的。边双连通分量表示求出几个最大的点集,使得任意一个点集中点两两双连通。例题luoguP8436方法1我们发现,如果两个节点原先连通但不是双连通,肯定他们之间的路径是经过某一座桥,所以可以求出来桥,把桥拆......
  • 聚水潭与金蝶云星空对接集成退货退款查询连通[聚水潭][销售退货单标准新增]-v1(聚水潭
    聚水潭与金蝶云星空对接集成退货退款查询连通[聚水潭][销售退货单标准新增]-v1(聚水潭--销售退货对接-P-12495392-这个店铺的数据)接入系统:聚水潭聚水潭是SaaS协同平台、电商ERP软件。聚水潭成立于2014年,创始人兼CEO骆海东拥有近三十年传统及电商ERP的研发和实施部署经验。......
  • [转]Docker 两个不同网络间实现连通
    原文地址:Docker两个不同网络间实现连通-西瓜君~-博客园一、启动不同网络的容器1、启动两个bridge(自带默认)桥接的容器[root@yang~]#dockerrun-it--nametomcat1tomcat[root@yang~]#dockerrun-it--nametomcat2tomcat#查看容器[root@yang~]#dockerps......
  • Python环境下一种改进小波分解方法-用于多分量信号的分解
    小波通俗的讲就是一种振幅表现为在正负之间震荡的波形。小波变换在基于短时傅立叶变换的前提下,又加入了其所没有的可随频率变化的“时间-频率”窗口,其能对时间、频率进行局部化分析,并且对待处理信号通过多尺度处理使其表现为时-频细分的特点,是一种能突出信号时频特点以及细节的......
  • 强连通分量随记随忘
    vis用于判断某个点是否在栈中tot表示强连通分量的数量belong[x]表示点x所属的强连通分量all[]与tot变量相关,表示此强连通分量的点的数量outd[]与tot变量相关,表示此强连通分量的出度模板代码如下:#include<bits/stdc++.h>usingnamespacestd;constintN=1e4+5;intn,m,......