2022-11-07:给你一个 n 个节点的 有向图 ,节点编号为 0 到 n - 1 ,其中每个节点 至多 有一条出边。 图用一个大小为 n 下标从 0 开始的数组 edges 表示, 节点 i 到
2022-11-07:给你一个 n 个节点的 有向图 ,节点编号为 0 到 n - 1 ,其中每个节点 至多 有一条出边。
图用一个大小为 n 下标从 0 开始的数组 edges 表示,
节点 i 到节点 edges[i] 之间有一条有向边。如果节点 i 没有出边,那么 edges[i] == -1 。
请你返回图中的 最长 环,如果没有任何环,请返回 -1 。
输入:edges = [3,3,4,2,3]。
输出:3。
答案2022-11-07:
一个环指的是起点和终点是 同一个 节点的路径。
用强联通分量。
代码用rust编写。代码如下:
use std::iter::repeat;
impl Solution {
pub fn longest_cycle(edges: Vec<i32>) -> i32 {
let n = edges.len() as i32;
let mut graph: Vec<Vec<i32>> = repeat(vec![]).take(n as usize).collect();
for i in 0..n {
if edges[i as usize] != -1 {
graph[i as usize].push(edges[i as usize]);
}
}
let mut connected_components = StronglyConnectedComponents::new(graph);
let m = connected_components.get_sccn() + 1;
let mut cnt: Vec<i32> = repeat(0).take(m as usize).collect();
let scc = connected_components.get_scc();
for i in 0..n {
cnt[scc[i as usize] as usize] += 1;
}
let mut ans = -1;
for count in cnt.iter() {
ans = get_max(ans, if *count > 1 { *count } else { -1 });
}
return ans;
}
}
struct StronglyConnectedComponents {
nexts: Vec<Vec<i32>>,
n: i32,
stack_size: i32,
cnt: i32,
sccn: i32,
stack: Vec<i32>,
dfn: Vec<i32>,
low: Vec<i32>,
scc: Vec<i32>,
}
impl StronglyConnectedComponents {
pub fn new(edges: Vec<Vec<i32>>) -> Self {
let mut ans: StronglyConnectedComponents = StronglyConnectedComponents {
nexts: edges,
n: 0,
stack_size: 0,
cnt: 0,
sccn: 0,
stack: vec![],
dfn: vec![],
low: vec![],
scc: vec![],
};
ans.init();
ans.scc();
return ans;
}
fn init(&mut self) {
self.n = self.nexts.len() as i32;
self.stack_size = 0;
self.cnt = 0;
self.sccn = 0;
self.stack = repeat(0).take(self.n as usize).collect();
self.dfn = repeat(0).take(self.n as usize).collect();
self.low = repeat(0).take(self.n as usize).collect();
self.scc = repeat(0).take(self.n as usize).collect();
}
fn scc(&mut self) {
for i in 0..self.n {
if self.dfn[i as usize] == 0 {
self.tarjan(i);
}
}
}
fn tarjan(&mut self, p: i32) {
self.cnt += 1;
self.dfn[p as usize] = self.cnt;
self.low[p as usize] = self.dfn[p as usize];
self.stack[self.stack_size as usize] = p;
self.stack_size += 1;
for q in self.nexts[p as usize].clone().iter() {
if self.dfn[*q as usize] == 0 {
self.tarjan(*q);
}
if self.scc[*q as usize] == 0 {
self.low[p as usize] = get_min(self.low[p as usize], self.low[*q as usize]);
}
}
if self.low[p as usize] == self.dfn[p as usize] {
self.sccn += 1;
let mut top = 0;
self.stack_size -= 1;
top = self.stack[self.stack_size as usize];
self.scc[top as usize] = self.sccn;
while top != p {
self.stack_size -= 1;
top = self.stack[self.stack_size as usize];
self.scc[top as usize] = self.sccn;
}
}
}
fn get_scc(&mut self) -> &Vec<i32> {
return &self.scc;
}
fn get_sccn(&mut self) -> i32 {
return self.sccn;
}
}
fn get_min<T: Clone + Copy + std::cmp::PartialOrd>(a: T, b: T) -> T {
if a < b {
a
} else {
b
}
}
fn get_max<T: Clone + Copy + std::cmp::PartialOrd>(a: T, b: T) -> T {
if a > b {
a
} else {
b
}
}
fn main() {
let edges = vec![3, 3, 4, 2, 3];
let ans = Solution::longest_cycle(edges);
println!("ans = {}", ans);
let edges = vec![2, -1, 3, 1];
let ans = Solution::longest_cycle(edges);
println!("ans = {}", ans);
}
struct Solution {}
执行结果如下:

2022-11-07:给你一个 n 个节点的 有向图 ,节点编号为 0 到 n - 1 ,其中每个节点 至多 有一条出边。 图用一个大小为 n 下标从 0 开始的数组 edges 表示, 节点 i 到的更多相关文章
- POJ 1236--Network of Schools【scc缩点构图 && 求scc入度为0的个数 && 求最少加几条边使图变成强联通】
Network of Schools Time Limit: 1000MS Memory Limit: 10000K Total Submissions: 13325 Accepted: 53 ...
- 11.07图论水题Test
11.07图论水题Test 题目 描述 做法 \(BSOJ6378\) 在\(i\)位置可以到\(i+a_i\)或\(i+b_i\)求\(1\rightarrow n\)字典序最小路径 判可达性后贪心 ...
- 在主方法中定义一个大小为10*10的二维字符型数组,数组名为y,正反对角线上存的是‘*’,其余 位置存的是‘#’;输出这个数组中的所有元素。
//在主方法中定义一个大小为10*10的二维字符型数组,数组名为y,正反对角线上存的是‘*’,其余 位置存的是‘#’:输出这个数组中的所有元素. char [][]y=new char [10][10 ...
- 在主方法中定义一个大小为50的一维整型数组,数组i名为x,数组中存放着{1,3,5,…,99}输出这个数组中的所有元素,每输出十个换一行
package hanqi; import java.util.Scanner; public class Test7 { public static void main(String[] args) ...
- 一个大小为N的数组,里面是N个整数,怎样去除重复的数
题目:一个大小为N的数组,里面是N个整数,怎样去除重复的数字: 要求时间复杂度为O(n),空间复杂度为O(1). 需要除掉重复的整数的数组,注意这里我没有处理负数情况,其实负数情况只要先用0快排分一下 ...
- 每天一个JS 小demo之韩雪冬轮播图。主要知识点:html,css布局,对于数组和对象的理解和运用
@charset "utf-8"; /* CSS Document */ ;; } li { list-style: none; } img { border: none; } b ...
- 假设一个大小为100亿个数据的数组,该数组是从小到大排好序的,现在该数组分成若干段,每个段的数据长度小于20「也就是说:题目并没有说每段数据的size 相同,只是说每个段的 size < 20 而已」
假设一个大小为100亿个数据的数组,该数组是从小到大排好序的,现在该数组分成若干段,每个段的数据长度小于20「也就是说:题目并没有说每段数据的size 相同,只是说每个段的 size < 20 ...
- Java 返回字符串中第一个不重复字符的下标 下标从0开始
比如abcdefgabdef 其中字符c和g不重复,返回c的小标,下标从0开始,那么是2 package com.example.demo; import org.testng.annotations ...
- ROC曲线是通过样本点分类概率画出的 例如某一个sample预测为1概率为0.6 预测为0概率0.4这样画出来,此外如果曲线不是特别平滑的话,那么很可能存在过拟合的情况
ROC和AUC介绍以及如何计算AUC from:http://alexkong.net/2013/06/introduction-to-auc-and-roc/ ROC(Receiver Operat ...
- 2022.11.15 NOIP2022 模拟赛十
炸弹威力 Source:洛谷 P6036. 记 \(f_{i,0/1}\) 表示第 \(i\) 个位置为 \(0/1\) 的答案个数,有 DP 转移: \[\begin{aligned} (1-p_i ...
随机推荐
- svn备份迁移
参考链接: SVN版本库的迁移 dump的详细使用 https://www.iteye.com/blog/tdcq-1684344 svn备份与还原_脚本_(dump命令)
- Mysql 行号+分组行号+取Top记录 SQL
Mysql 行号+分组行号+取Top记录 SQL select * from ( SELECT (@rowNum := @rowNum + 1) as rowNum -- 全量行号 , a.col1 ...
- 初始化时使window 全屏 且显示任务栏 wpf
void IniWindowFullScreemAndDisplayTaskbar() { this.Width = SystemParameters.FullPrimaryScreenWidth; ...
- Qt 5.15.2 QTextEdit无法设置新字体的处理方式
首发于我的个人博客:xie-kang.com 博客内有更多文章,欢迎大家访问 原文地址 在使用QT 5.15.2 开发的过程中碰到了件怪事,下列代码无法给QTextEdit选中的文字设置字体: QTe ...
- Rethinking Table Recognition using Graph Neural Networks
摘要:CNN用来视觉特征提取:图网络用来处理结构问题:由于缺少大量的数据,作者建立了一个合成数据集的数据库. 关键词:表格识别,结果分析:图神经网络,文档模型:图模型:数据库 源码地址;https:/ ...
- DVWA-XSS (Stored) 存储型XSS
存储型XSS,顾名思义,就是会传入数据库,长久的使用,常见为留言板,用户信息资料. LOW 审计源码 <?php // 是否提交 btnSign if( isset( $_POST[ 'btnS ...
- 数据库中1NF,2NF,3NF的判别
参照:https://blog.csdn.net/qq_28888837/article/details/98733448 1NF:每一个都是最原子化. 2NF:找到主键后,每一个非主键对主键都是完 ...
- MySQL高可用架构-MMM、MHA、MGR、分库分表
总结 MMM是是Perl语言开发的用于管理MySQL主主同步架构的工具包.主要作用:管理MySQL的主主复制拓扑,在主服务器失效时,进行主备切换和故障转移. MMM缺点:故障切换可能会丢事务(主备使用 ...
- 怎么在php7项目中安装event扩展
今天就跟大家聊聊有关怎么在php7项目中安装event扩展,可能很多人都不太了解,为了让大家更加了解,小编给大家总结了以下内容,希望大家根据这篇文章可以有所收获. 安装支持库libevent wget ...
- node-sass与node版本对照图