Всем привет Есть достаточно базовая задача: Дан неориентированный граф. Требуется определить, есть

ли в нем цикл, и, если есть, вывести его.

Входные данные подаются в виде матрицы смежности. Надо определить, есть ли цикл и восстановить его. Кажется что задача вполне себе базовая, нужно запоминать массив родителей чтобы успешно восстановить цикл. У меня получился такой код: https://pastecode.io/s/5mbbjioe
fun findCycle(n: Int, graph: Array<IntArray>): List<Int>? {
val visited = BooleanArray(n)
val parent = IntArray(n) { -1 }

fun dfs(v: Int): List<Int>? {
visited[v] = true
for (u in 0 until n) {
if (graph[v][u] == 1) {
if (!visited[u]) {
parent[u] = v
val cycle = dfs(u)
if (cycle != null) return cycle
} else if (parent[v] != u) {
val cycle = mutableListOf<Int>()
var cur = v
while (cur != -1) {
cycle.add(cur + 1)
cur = parent[cur]
}
return cycle.reversed()
}
}
}
return null
}

for (v in 0 until n) {
if (!visited[v]) {
val cycle = dfs(v)
if (cycle != null) return cycle
}
}

return null
}


Но у меня решение валится на одном из тестов, не могу понять где же сделал ошибку, не подскажите где она может быть?

10 ответов

47 просмотров

что за язык прог.е?

Αλeksandr- Автор вопроса

L22, while (cur != -1) {, кмк, условие неправильное; допустим, мы зашли в компоненту графа, хвостик не образующий цикла, и цикл. Тут мы выведем цикл и хвостик, а надо только до начала цикла.

конечно, надо поработать над стилем, читать очень неудобно (в частности visit стоит проверять внутри функции dfs) > Дан неориентированный граф. Требуется определить, есть ли в нем цикл то есть определить, что одна из компонент связности имеет |E| >= |V| ? > while (cur != -1) while (cur != u) мб?

Αλeksandr- Автор вопроса
Yuriy
L22, while (cur != -1) {, кмк, условие неправильно...

Хм, похоже на правду, т.е получается вот так примерно fun processCycle(v: Int, n: Int) { var curr = v while (parent[curr] != n) { cycle.add(curr) curr = parent[curr] } }

Αλeksandr- Автор вопроса
Constantine Drozdov
конечно, надо поработать над стилем, читать очень ...

Про стиль не совсем понял коммент, я написал этот код по шаблону на самом деле с одной лекции

Не знаю что вы делаете, но пмсм если цель обнаружить цикл, то есть известная тема с двумя указателями - один переходит один узел за раз, другой два узла, соотвественно если цикла нет от стартового узла, то более шустрый указатель выйдет к листу, если цикл есть, то в какой-то момент попадя в цикл один указатель догонит второй за меньше чем 2N+K, где N - длина цикла, K длина цепочки вне цикла, последующее восстановление возможно просто запоминанием точки встречи и полным проходом по циклу. Массив родителей я бы не хранил, если конечно у вас не какой-то сверхтривиальный и миниатюрный граф, в котором цепочка вне цикла будет очень короткой, единственное что возможно был бы смысл дополнительно вести стек пар "узел, узел_перехода", дабы по нему принимать решения о посещениях узлов с несколькими исходящими рёбрами.

Αλeksandr- Автор вопроса
Александр
Не знаю что вы делаете, но пмсм если цель обнаружи...

Цель не просто обнаружить цикл, а восстановить его. Ну ив графах все-таки обычно используют DFS с "цветами", где: 0 - непосещенная вершина (white) 1 - вершина уже посещалась, но не закончена процесситься (grey) 2 - вершина закончена процессится (black)

Александр
Не знаю что вы делаете, но пмсм если цель обнаружи...

Кажется, что вы какую-то другую задачу имеете в виду

Похожие вопросы

Обсуждают сегодня

Привет всем. Подскажите, как можно данную задачу более менее эффективно решить? В столовой одного известного Завода вот-вот начнётся обед. На обеде есть три гарнира — макарош...
Vitaliy
6
Всем привет Пытаюсь решить следующую задачу: https://informatics.msk.ru/mod/statements/view.php?id=6992&chapterid=101#1 Строка S была записана много раз подряд, после чего из ...
Αλeksandr
10
всем привет. У меня есть неупорядоченный массив точек(в моем случае в трёхмерном пространстве). Есть критерий связанности точек: если евклидово расстояние между ними меньше за...
Павлик Ливаткин
31
Доброе утро. Такой вопрос: есть ли какие-то практически полезные меры вычислительной мощности (в смысле computational complexity) для реальных машин, с ограниченными ресурсам...
Yaroslav Schekin
15
Друзья, практический вопрос надо счиать скользящую медиану в последовательности по заданному окну (длины N) тупой вариант - взять значения в окне, отсортировать, взять элеме...
Стас Выщепан
17
Здравствуйте. Есть задача нужно найти наименшое число P где фактриал P делиться на 10^N. Ограничения 10^9. Знаю что нужно найти такой P в конце как минимум N нулей. Решение с ...
. Azmiddin
20
#pragma once #include <iostream> #include <vector> template <typename T, typename Comp = std::less<T>> class Heap { public: Heap() = default; Heap(const std::vector<T>&...
Степан
1
Должна-ли работать такая стратегия: Мы каждую секунду бросаем монетку - орел или решка. Если орел - покупаем акцию на все деньги, если у нас есть деньги, или продаем все акци...
George Polevoy
13
Как можно сжимать временные ряды в памяти? У меня есть исторические стоимости ценных бумаг. Данные для каждой минуты в истории OHLC (Open, High, Low, Close). Соответственно, O...
George Polevoy
10
Здравствуйте. Мне надо найти Kth Smallest Sum of Two Sorted Arrays за O(k log k). Например, если A = {1, 2, 3}, а B = {2, 3, 4}, то A + B = {3, 4, 5, 4, 5, 6, 5, 6, 7}, тогда...
Степан
9
Карта сайта