Как найти радиус дерева

Содержание

  1. Алгоритмы на деревьях
  2. Содержание
  3. Диаметр дерева
  4. Алгоритм
  5. Реализация
  6. Обоснование корректности
  7. Оценка времени работы
  8. Центр дерева
  9. Определения
  10. Алгоритм
  11. Наивный алгоритм
  12. Алгоритм для дерева за O(n)
  13. Доказываем корректность поиска диаметра дерева
  14. Радиус, диаметр и центр графа

Алгоритмы на деревьях

Содержание

Диаметр дерева

Определение:
Диаметр дерева (англ. diameter of a tree) — максимальная длина (в рёбрах) кратчайшего пути в дереве между любыми двумя вершинами.

Пусть дан граф [math]G = langle V, E rangle [/math] . Тогда диаметром [math]d[/math] называется [math]maxlimits_ dist(v, u)[/math] , где [math]dist[/math] — кратчайшее расстояние между вершинами.

Алгоритм

  • Возьмём любую вершину [math] v in V [/math] и найдём расстояния до всех других вершин. [math]d[i] = dist(v, i)[/math]
  • Возьмём вершину [math] u in V [/math] такую, что [math]d[u] geqslant d[t][/math] для любого [math]t[/math] . Снова найдём расстояние от [math]u[/math] до всех остальных вершин. Самое большое расстояние — диаметр дерева.

Расстояние до остальных вершин будем искать алгоритмом [math]BFS[/math] .

Реализация

Обоснование корректности

Будем пользоваться свойством, что в любом дереве больше одного листа. Исключительный случай — дерево из одной вершины, но алгоритм сработает верно и в этом случае.

Доказательство: [math]triangleright[/math] Пусть искомое расстояние — расстояние между вершинами [math]a, b[/math] , где [math]b[/math] не является листом. Так как [math]b[/math] не является листом, то её степень больше единицы, следовательно, из неё существует ребро в непосещённую вершину (дважды посетить вершину [math]b[/math] мы не можем). [math]triangleleft[/math]

После запуска алгоритма получим дерево [math]BFS[/math] .

Доказательство: [math]triangleright[/math]

Предположим, существует ребро [math]u, v[/math] между соседними поддеревьями:

Рассмотрим первую вершину, в которую приведет наш алгоритм, пусть это вершина [math]u[/math] , тогда в ходе рассмотрения всех смежных вершин [math]u[/math] мы добавим в список вершину [math]v[/math] , тем самым исключив возможность попадания их в разные поддеревья. [math]triangleleft[/math]

Мы свели задачу к нахождению вершины [math]w[/math] , такой что сумма глубин поддеревьев максимальна.

Докажем, что одно из искомых поддеревьев содержит самый глубокий лист. Пусть нет, тогда, взяв расстояние от [math]w[/math] до глубочайшего листа, мы можем улучшить ответ.

Таким образом мы доказали, что нам нужно взять вершину [math]u[/math] с наибольшей глубиной после первого [math]BFS[/math] , очевидно, что ей в пару надо сопоставить вершину [math]w[/math] , такую что [math]dist(u, w)[/math] максимально. Вершину [math]w[/math] можно найти запуском [math]BFS[/math] из [math]u[/math] .

Оценка времени работы

Все операции кроме [math]BFS[/math] — [math]O(1)[/math] . [math]BFS[/math] работает за линейное время, запускаем мы его два раза. Получаем [math]O(|V| + |E|)[/math] .

Центр дерева

Определения

Определение:
Эксцентриситет вершины [math]e(v)[/math] (англ. eccentricity of a vertex) — [math]maxlimits_ dist(v, u)[/math] , где [math]V[/math] — множество вершин связного графа [math]G[/math] .
Определение:
Радиус [math]r(G)[/math] (англ. radius) — наименьший из эксцентриситетов вершин графа [math]G[/math] .
Определение:
Центральная вершина (англ. central vertex) — вершина графа [math]G[/math] , такая что [math]e(v) = r(G)[/math]
Определение:
Центр графа [math]G[/math] (англ. center of a graph) — множество всех центральных вершин графа [math]G[/math] .

Алгоритм

Наивный алгоритм

Найдём центр графа исходя из его определения.

  • Построим матрицу [math]A_[/math] ( [math]n[/math] — мощность множества [math]V[/math] ), где [math]a_ = d_[/math] , то есть матрицу кратчайших путей. Для её построения можно воспользоваться алгоритмом Флойда-Уоршелла или Дейкстры.
  • Подсчитаем максимум в каждой строчке матрицы [math]A[/math] . Таким образом, получим массив длины [math]n[/math] .
  • Найдём наименьший элемент в этом массиве. Эта вершина и есть центр графа. В том случае, когда вершин несколько, все они являются центрами.

Асимптотика зависит от используемого способа подсчета кратчайших путей. При Флойде это будет [math]O(V^3)[/math] , а при Дейкстре — максимум из асимптотики конкретной реализации Дейкстры и [math]O(V^2)[/math] , за которую мы находим максимумы в матрице.

Алгоритм для дерева за O(n)

Доказательство: [math]triangleright[/math] Утверждение очевидно для деревьев с одной и двумя вершинами. Покажем, что у любого другого дерева [math]T[/math] те же центральные вершины, что и у дерева [math]T'[/math] , полученного из [math]T[/math] удалением всех его висячих вершин. Расстояние от данной вершины дерева [math]u[/math] до любой другой вершины [math]v[/math] достигает наибольшего значения, когда [math]v[/math] – висячая вершина. Таким образом, эксцентриситет каждой вершины дерева [math]T'[/math] точно на единицу меньше эксцентриситета этой же вершины в дереве [math]T[/math] , следовательно, центры этих деревьев совпадают. Продолжим процесс удаления и получим требуемое. [math]triangleleft[/math]

Собственно, алгоритм нахождения центра описан в доказательстве теоремы.

  • Пройдёмся по дереву обходом в глубину и пометим все висячие вершины числом [math]0[/math] .
  • Обрежем помеченные вершины.
  • Образовавшиеся листья пометим числом [math]1[/math] и тоже обрежем.
  • Будем повторять, пока на текущей глубине не окажется не более двух листьев, и при этом в дереве будет тоже не более двух листьев.

Оставшиеся листья являются центром дерева.

Для того, чтобы алгоритм работал за [math]O(n)[/math] , нужно обрабатывать листья по одному, поддерживая в очереди два последовательных по глубине слоя.

Источник

Доказываем корректность поиска диаметра дерева

Однажды на зачете мне попалась следующая задача. Придумайте алгоритм, находящий две вершины дерева с максимальным расстоянием друг от друга, и докажите его корректность. В тот момент я в принципе не знала, что у деревьев есть диаметр, радиус и много прочих вещей. Уже после зачета друг просветил меня, рассказав, что это за алгоритм, но без доказательства. Именно вопросом о доказательстве долгое время была забита моя голова. После прочтения нескольких статей, стало понятно, что материал не уляжется, пока самостоятельно себе не объясню все практически на пальцах (может, и читателю придется по вкусу). Перейдем от демагогии к сути.

Диаметр дерева — это максимальное расстояние между двумя вершинами в дереве. Алгоритм поиска состоит в двух запусках BFS. Первый идет от произвольной вершины дерева, во время обхода насчитываются расстояния от текущей вершины до всех других. Затем из них выбирается самая удаленная. Из нее делается второй запуск BFS. Насчитываются новые расстояния. Максимальное среди них и будет диаметром.

Почему этот простой с виду алгоритм работает корректно?

Чтобы избежать подводных камней при доказательстве, сразу обговорим случай с деревом из одной вершины и из двух вершин. Если вершина одна, то ребер у нас нет, первый BFS сообщит, что стартовая вершина имеет максимальную глубину, второй — тоже. По сути это и есть так, алгоритм сработает верно. Если имеется две вершины, то первый обход придет во вторую вершину, а второй — в стартовую, что корректно для данного случая.

Сначала поймем, что искомое расстояние — расстояние между двумя листами. На самом деле, пусть вершина на конце найденного максимального путь не является листом. Одновременно мы не можем увеличить искомое расстояние по предположению. Тем не менее, это означает, что BFS не посетил вершины, «расположенные за» текущей, что противоречит корректности BFS. Получается, что обе найденные вершины будут листьями. Прекрасно.

Подвесим наше дерево за вершину v, из которой запускаем первый обход.

Рассмотрим отдельный случай, когда вершина v сама является листом. В случае, если она и есть первый конец диаметра, то очевидно, что первый BFS найдет второй конец, а второй вернется в стартовую вершину. Иначе диаметр не будет проходить через v и также будет «перегибаться», так как не может содержать более двух листьев.

Пусть мы нашли диаметр и две вершины, ему соответствующие. Найдем LCA этих вершин a и b, назовем эту вершину c. Очевидно, что D = d[a,c] + d[c,b]. Фактически диаметр это сумма двух наиболее глубоких поддеревьев некоторой вершины, если она принадлежит длиннейшему пути. Диаметр дерева — это максимальный диаметр среди всех поддеревьев. Первый обход в ширину даст нам максимальную по глубине вершину (так как мы подвесили за стартовую вершину). Обозначим вершину на конце найденного пути w. Докажем, что w будет принадлежать искомому длиннейшему пути. Пусть диаметр «перегибается» в вершине c(он будет «перегибаться», так как соединяет два листа, а дерево подвешено за вершину v, не являющуюся листом). Пускай вершина w принадлежит одному из поддеревьев вершины c. Тогда просто заменим некоторую часть пути (c, x), где x — один из концов, на (c, w). d[c,x] d[x,c]. d[w,e] > d[y,e] > d[y,c]. Поэтому D0 = d[x,c] + d[y,c] d[a,w] по предположению;
В итоге получаем противоречие. Поэтому вершина w обладает наибольшей глубиной в любом поддереве.

Получаем, что вершина w принадлежит диаметру, а также является одним из его концов. Тогда очевидно, что остается лишь найти наиболее удаленную от w вершину, что и делает второй BFS.

Источник

Радиус, диаметр и центр графа

Вычисление расстояний и определение маршрутов в графе являются одной из наиболее очевидных и практичных задач, которые возникают в теории графов. Введем некоторые необходимые определения.

Эксцентриситет вершины графа – расстояние до максимально удаленной от нее вершины. Для графа, для которого не определен вес его ребер, расстояние определяется в виде числа ребер.

Радиус графа – минимальный эксцентриситет вершин, а диаметр графа – максимальный эксцентриситет вершин.

Центр графа образуют вершины, у которых эксцентриситет равен радиусу. Центр графа может состоять из одной, нескольких или всех вершин графа.

Периферийные вершины имеют эксцентриситет, равный диаметру.

Простая цепь с длиной, равной диаметру графа, называется диаметральной.

Теорема 12.1. В связном графе диаметр не больше ранга его матрицы смежности.

Теорема 12.2. (Жордана) Каждое дерево имеет центр, состоящий из одной или двух смежных вершин.

Теорема 12.3. Если диаметр дерева четный, то дерево имеет единственный центр, и все диаметральные цепи проходят через него, если диаметр нечетный, то центров два и все диаметральные цепи содержат ребро, их соединяющее.

Очевидно практическое значение центра графа. Если, например, речь идет о графе дорог с вершинами-городами, то в математическом центре целесообразно размещать административный центр, складские помещения и т.п. Этот же подход можно применять и для взвешенного графа, где расстояния – это веса ребер. В качестве веса можно брать евклидовое расстояние, время или стоимость передвижения между пунктами.

Пример 12.5. Найти радиус, диаметр и центр графа, изображенного на рис. 12.1.

Решение. В данной задаче удобно использовать матрицу расстояний S. Элемент этой квадратной симметричной матрицы равен расстоянию между вершиной i и вершиной j. Для графа, показанного на рис. 12.1, матрица расстояний имеет следующий вид:

. (12.2)

Вычислим эксцентриситет каждой вершины. Эту величину можно определить как максимальный элемент соответствующего столбца матрицы расстояний (или строки – поскольку матрица S симметрична). Получаем

Радиус графа r – минимальный эксцентриситет вершин. В данном случае r = 2. Такой эксцентриситет имеют вершины № 2, № 4 и № 5. Эти вершины образуют центр графа. Диаметр графа d – максимальный эксцентриситет вершин. В данном случае d = 3. Такой эксцентриситет имеют вершины № 1 и № 3, это периферия графа. В исследованном графе вершины оказались либо центральными, либо периферийными. В графах большего порядка существуют и другие вершины.

Эксцентриситеты вершин небольшого графа легко вычислять непосредственным подсчетом по рисунку. Однако не всегда граф задан своим рисунком. Кроме того, граф может иметь большой размер. Поэтому необходим другой способ решения предыдущей задачи. Известна следующая теорема.

Теорема 12.4. Пусть – матрица смежности графа G без петель и , где . Тогда равно числу маршрутов длины k от вершины к вершине .

Решение задач теории графов с помощью различных преобразований матрицы смежности называют алгебраическим методом.

Пример 12.6. Найти матрицу расстояний графа, изображенного на рис. 12.1, алгебраическим методом.

Решение. Матрица смежности данного графа равна:

.

Будем заполнять матрицу расстояний, рассматривая степени матрицы смежности. Единицы матрицы смежности показывают пары вершин, расстояние между которыми равно единице (т.е. они соединены одним ребром).

.

Диагональные элементы матрицы расстояний – нули. Умножаем матрицу смежности на себя:

.

Согласно теореме между вершинами 2 и 3, 1 и 4 и т.д. имеется некоторое число маршрутов длиной 2 (поскольку степень матрицы равна двум). Число маршрутов здесь не используется, важен сам факт наличия маршрута и его длина, на что и указывает ненулевой элемент степени матрицы, не совпадающий с элементом, отмеченным при вычислении маршрута меньшей длины. Проставляем 2 в незаполненные элементы матрицы расстояний и получаем следующее приближение:

.

Осталось неизвестным расстояние между вершинами 1 и 3. Будем умножать матрицу смежности саму на себя до тех пор, пока в матрице не появится ненулевой элемент . Тогда соответствующий элемент матрицы расстояний равен степени матрицы смежности: . На следующем шаге получаем

,

следовательно, , и окончательно

.

Полученная матрица совпадает с матрицей расстояний S (12.2), найденной непосредственными вычислениями по рисунку.

Содержание

  • 1 Диаметр дерева
    • 1.1 Алгоритм
    • 1.2 Реализация
    • 1.3 Обоснование корректности
    • 1.4 Оценка времени работы
  • 2 Центр дерева
    • 2.1 Определения
    • 2.2 Алгоритм
      • 2.2.1 Наивный алгоритм
      • 2.2.2 Алгоритм для дерева за O(n)
  • 3 См. также
  • 4 Источники информации

Диаметр дерева

Определение:
Диаметр дерева (англ. diameter of a tree) — максимальная длина (в рёбрах) кратчайшего пути в дереве между любыми двумя вершинами.

Пусть дан граф . Тогда диаметром называется , где — кратчайшее расстояние между вершинами.

Алгоритм

  • Возьмём любую вершину и найдём расстояния до всех других вершин.
  • Возьмём вершину такую, что для любого . Снова найдём расстояние от до всех остальных вершин. Самое большое расстояние — диаметр дерева.

Расстояние до остальных вершин будем искать алгоритмом .

Реализация

//граф g представлен списком смежности 
int diameterTree(list<list<int>> g):        
    v = u = w = 0
    d = bfs(g, v)
    for i = 0, i < n, i++
         if d[i] > d[u]
              u = i
    d = bfs(g, u)
    for i = 0, i < n, i++
          if d[i] > d[w]
               w = i
    return d[w]

Обоснование корректности

Будем пользоваться свойством, что в любом дереве больше одного листа. Исключительный случай — дерево из одной вершины, но алгоритм сработает верно и в этом случае.

Теорема:

Искомое расстояние — расстояние между двумя листами.

Доказательство:
Пусть искомое расстояние — расстояние между вершинами , где не является листом. Так как не является листом, то её степень больше единицы, следовательно, из неё существует ребро в непосещённую вершину (дважды посетить вершину мы не можем).

После запуска алгоритма получим дерево .

Теорема:

В дереве не существует ребер между вершинами из разных поддеревьев некоторого их общего предка.

Доказательство:

Предположим, существует ребро между соседними поддеревьями:

Рассмотрим первую вершину, в которую приведет наш алгоритм, пусть это вершина , тогда в ходе рассмотрения всех смежных вершин мы добавим в список вершину , тем самым исключив возможность попадания их в разные поддеревья.

Мы свели задачу к нахождению вершины , такой что сумма глубин поддеревьев максимальна.

Докажем, что одно из искомых поддеревьев содержит самый глубокий лист.
Пусть нет, тогда, взяв расстояние от до глубочайшего листа, мы можем улучшить ответ.

Таким образом мы доказали, что нам нужно взять вершину с наибольшей глубиной после первого , очевидно, что ей в пару надо сопоставить вершину , такую что максимально. Вершину можно найти запуском из .

Оценка времени работы

Все операции кроме — .
работает за линейное время, запускаем мы его два раза. Получаем .

Центр дерева

Определения

Определение:
Эксцентриситет вершины (англ. eccentricity of a vertex) — , где — множество вершин связного графа .
Определение:
Радиус (англ. radius) — наименьший из эксцентриситетов вершин графа .
Определение:
Центральная вершина (англ. central vertex) — вершина графа , такая что
Определение:
Центр графа (англ. center of a graph) — множество всех центральных вершин графа .

Примеры деревьев с одной и двумя центральными вершинами

Графы, у которых показан эксцентриситет каждой вершины

Алгоритм

Наивный алгоритм

Найдём центр графа исходя из его определения.

  • Построим матрицу ( — мощность множества ), где , то есть матрицу кратчайших путей. Для её построения можно воспользоваться алгоритмом Флойда-Уоршелла или Дейкстры.
  • Подсчитаем максимум в каждой строчке матрицы . Таким образом, получим массив длины .
  • Найдём наименьший элемент в этом массиве. Эта вершина и есть центр графа. В том случае, когда вершин несколько, все они являются центрами.

Асимптотика зависит от используемого способа подсчета кратчайших путей. При Флойде это будет , а при Дейкстре — максимум из асимптотики конкретной реализации Дейкстры и , за которую мы находим максимумы в матрице.

Алгоритм для дерева за O(n)

Теорема:

Каждое дерево имеет центр, состоящий из одной вершины или из двух смежных вершин.

Доказательство:
Утверждение очевидно для деревьев с одной и двумя вершинами. Покажем, что у любого другого дерева те же центральные вершины, что и у дерева , полученного из удалением всех его висячих вершин. Расстояние от данной вершины дерева до любой другой вершины достигает наибольшего значения, когда – висячая вершина. Таким образом, эксцентриситет каждой вершины дерева точно на единицу меньше эксцентриситета этой же вершины в дереве , следовательно, центры этих деревьев совпадают. Продолжим процесс удаления и получим требуемое.

Собственно, алгоритм нахождения центра описан в доказательстве теоремы.

  • Пройдёмся по дереву обходом в глубину и пометим все висячие вершины числом .
  • Обрежем помеченные вершины.
  • Образовавшиеся листья пометим числом и тоже обрежем.
  • Будем повторять, пока на текущей глубине не окажется не более двух листьев, и при этом в дереве будет тоже не более двух листьев.

Оставшиеся листья являются центром дерева.

Для того, чтобы алгоритм работал за , нужно обрабатывать листья по одному, поддерживая в очереди два последовательных по глубине слоя.

См. также

  • Дерево, эквивалентные определения
  • Дополнительный, самодополнительный граф

Источники информации

  • Wikipedia — Distance (graph theory)
  • Ф. Харари: Теория графов
  • А. Клебанов: Центры графов(нерабочая ссылка)

Нахождение центра, радиуса и диаметра дерева, заданного двоичным кодом

Алгоритм позволяет найти количество вершин, образующих центр, диаметр и радиус дерева, заданного двоичным кодом

Постановка задачи

Исходные данные берутся из файла input.txt. В первой строке записано одно число n — количество вершин в дереве. Во второй строке располагается двоичный код. Нужно записать три числа в файл output.txt количество вершин, образующих центр, радиус и диаметр.

Использованые структуры данных

Для реализиации списка смежности был использован std::vector

Пример решённой задачи

Для входных данных

Корректным решением является:

Краткий алгоритм

  • Создаем список смежности из двоичного кода
  • Считаем диаметр
  • Считаем радиус
  • Находим центровые вершины

Создание списка смежности из двоичного кода

Для этого используем функцию

std::vector<std::vector<int>> ReadTree(std::istream &in) {
  std::vector<std::vector<int>> tree(1);
  ReadTreeRec(in, tree, 0);
  return std::move(tree);
}

Она принимает в качестве аргумента входящий поток std::istream &in и создает список смежности на базе std::vector<std::vector<int>> первая его координата — рассматриваемая вершина, вторая &mdash вершина, которая ей смежна.
Например список смежности для дерева, заданного двоичным кодом 0011 будет выглядеть так:

image

То есть по сути, наш список смежности выглядит так:

tree[c][0] = v — вершина c смежна вершине v

Создается он следующим образом:

Вызывается рекурсивная функция

void ReadTreeRec(std::istream &in, std::vector<std::vector<int>> &tree, int v) {
  ...
}

Кроме входящего потока, она принимает, собственно, список смежности, который требуется заполнить и параметр int v — индекс вершины

Работает он так:

void ReadTreeRec(std::istream &in, std::vector<std::vector<int>> &tree, int v) {
  for (char command; in >> command && command != '1';) {
    int u = tree.size();
    tree.emplace_back();  //create in end
    tree[v].push_back(u); //create and push
    tree[u].push_back(v);
    ReadTreeRec(in, tree, u);
  }
}
  • Из входящего потока считывается двоичный код
  • Если считываемый символ command != '1' тогда
    • создается переменная u равная текущему размеру списка смежностиtree.size()
    • создается очередная вершина с индексом v
    • в список смежности tree[v].push_back(u) кладется смежная с ней u
    • для u делается то же самое: tree[u].push_back(v)
    • рекурсивно вызывается эта же функция, но уже от вершины с индексом u

Довольно логично, что каждую инициализацию переменная u = tree.size() будет равна индексу очередной вершины в списке смежности

Когда мы получили список смежности, возвращаем его без копирования return std::move(tree)

Считаем диаметр

Теперь когда мы имеем список смежности для дерева, мы можем посчитать диаметр дерева.

Считать будем следующим образом:

  • найдем самое большое расстояние от корня дерева до крайней вершины
  • найдем самое большое расстояние от этой вершины до других вершин

Функция, возвращающая диаметр дерева выглядит так:

int CountDiameterLength(std::vector<std::vector<int>> &tree) {
  int vertices_count = tree.size();
  std::vector<int> distances(vertices_count);
  CountMaxDistanceRec(tree, distances, -1, 0);
  int new_root = FindVertexWithMaxDistance(distances);
  distances[new_root] = 0;
  CountMaxDistanceRec(tree, distances, -1, new_root);
  return distances[FindVertexWithMaxDistance(distances)];
}

В качестве аргумента она принимает ссылку на список смежности, созданный ранее

  • int vertices_count = tree.size() запоминаем количество вершин и создаем массив такого размера std::vector<int> distances(vertices_count)
  • заполним этот массив расстояниями от корня дерева с помощью функции void CountMaxDistanceRec(const std::vector<std::vector<int>> &tree, std::vector<int> &distances, int p, int v) — она будет описана ниже
  • от нового “нового корня” (т.е. от той вершины, расстояние до которой будет максимально) также запишем новые расстояния
  • вернем максимальное расстояние, находящееся в массиве расстояний по индексу, возвращаемому функцией FindVertexWithMaxDistance(distances) (реализациия её тривиальна, описываться не будет)

Как работает void CountMaxDistanceRec(const std::vector<std::vector<int>> &tree, std::vector<int> &distances, int p, int v) ?

Она принимает ссылку на список смежности, ссылку на массив расстояний индекс родительского элемента (для корня это -1) и индекс элемента, от которого считаются расстояния

  • Проходимся по всем вершинам, кроме родительской
  • Считаем рекурсивно расстояния до всех других вершин

То есть грубо говоря, мы прошлись DFS два раза

Считаем радиус

Делаем это по формуле radius = (diameter + 1) / 2

Считаем количество центров

По формуле center = (diameter) % 2 + 1

Тесты коррекности

Используем сайт graphonline

Тест 1

image

Входные данные:

Выходные данные:

image

Тест 2

image

Входные данные:

Выходные данные:

image

Тест 3

image

Входные данные:

12
0001010110110001011011

Выходные данные:

image

Тест 4

image

Входные данные:

Выходные данные:

image

Тест 5

image

Входные данные:

Выходные данные:

image

Тесты производительности

Для тестов производительности есть функция, возвращающая случайное дерево из n вершин в виде двоичного кода

Вот ее описание:

std::string tree_generator(int v_count) {
  std::random_device random_device;
  std::mt19937 generator(random_device());
  std::uniform_int_distribution<> distribution(0, 1);

  std::string generated = "";
  int count_0 = 0;
  int count_1 = 0;

  for (int i = 0; i < v_count * 2; ++i) {
    int x = distribution(generator);

    if (count_0 >= v_count) {
      x = 1;
      generated += x + 48;
      continue;
    }
    if (x == 1 && count_1 < count_0) {
      generated += x + 48;
      ++count_1;
    } else if (x == 1 && count_1 >= count_0) {
      x = 0;
      generated += x + 48;
      ++count_0;
    } else {
      generated += x + 48;
      x == 1 ? ++count_1 : ++count_0;
    }
  }

  return generated;
}

Таблица зависимости количества вершин и времени обработки алгоритмом

Количество Время(SEC)
1000 0.002
10000 0.008
25000 0.022
100000 0.071
500000 0.351
1000000 0.894
2000000 1.619
3000000 2.580
4000000 2.928
5000000 3.587
10000000 8.614
25000000 20.40
50000000 76.38
    1. Основные
      определения

Граф
– это совокупность двух множеств: вершини ребер,
между которыми определено отношениеинцидентности.

Каждое ребро e
из E
инцидентно ровно двум вершинам
и,
которые оно соединяет. При этом вершинаи реброe
называются инцидентными
друг другу, а вершины
иназываютсясмежными.

Принято обозначение
n
для числа вершин графа (мощность множества
):иm
для числа его ребер:
.
Говорят, что графG
есть (n,
m)
граф, где n
– порядок графа, m
– размер графа.

Если все ребра
графа неориентированные, т.е. пары
вершин, определяющие элементы множестваE,
неупорядочены, то такой граф называется
неориентированным графом, или неографом.
На рис. 12.1 показан пример неографа. Этот
граф имеет пять вершин и шесть ребер.

Рис. 12.1

Маршрут
– последовательность ребер, в которой
каждые два соседних ребра имеют общую
вершину. Граф связен,
если любые две вершины соединены хотя
бы одним маршрутом. Число ребер маршрута
определяет его длину.

Ребра, инцидентные
одной паре вершин, называются параллельными
или кратными.
Граф с кратными ребрами называется
мультиграфом.

Ребро
называетсяпетлей
(концевые вершины совпадают). Граф,
содержащий петли и кратные ребра,
называется псевдографом.
На рис. 12.2 показан псевдограф.

Рис. 12.2

Степень
deg(v)
вершины – это число ребер, инцидентных
v.
В неографе
сумма степеней всех вершин равна
удвоенному числу ребер

(лемма о рукопожатиях):

. (12.1)

Петля дает вклад,
равный 2, в степень вершины.

Степенная
последовательность

– последовательность степеней всех
вершин графа, записанная в определенном
порядке (по возрастанию или убыванию).

Пример
12.1.
Степенная
последовательность неографа, изображенного
на рис. 12.1, записанная по возрастанию,
выглядит так:

=1,
=2,=3,=3,=3.

Сумма степеней
всех вершин графа равна:

.

Этот результат
не противоречит лемме о рукопожатиях,
поскольку граф имеет шесть ребер (m
= 6).

Матрица
смежности

графа – квадратная матрица A
порядка n,
где элемент
равен числу ребер, соединяющих вершиныi
и j.

Пример 12.2.
Граф, показанный на рис. 12.1, имеет
следующую матрицу смежности

.

Матрица
инцидентности

I
– еще один способ описания графа. Число
строк этой матрицы равно числу вершин,
число столбцов – числу ребер;
=1,
если вершинаv
инцидентна ребру e;
в противном случае
=0.
В каждом столбце матрицы инцидентности
простого графа (без петель и без кратных
ребер) содержится по две единицы. Число
единиц в строке равно степени
соответствующей вершины.

Пример 12.3.
Граф, показанный на рис. 12.1, имеет
следующую матрицу инцидентности

.

Граф
называетсяподграфом
графа
,
еслии.
Если,
то подграф называетсяостовным.

Компонента
связности

графа – максимальный по включению
вершин и ребер связной подграф.

Ранг
графа
,
гдеk
– число компонент связности.

Дерево
– связной граф, содержащий n
– 1 ребро.

Пример 12.4.
На рис. 12.3 показано дерево, которое
одновременно является остовным подграфом
графа, показанного на рис. 12.1.

Рис. 12.3

    1. Радиус, диаметр
      и центр графа

Вычисление
расстояний и определение маршрутов в
графе являются одной из наиболее
очевидных и практичных задач, которые
возникают в теории графов. Введем
некоторые необходимые определения.

Эксцентриситет
вершины графа – расстояние до максимально
удаленной от нее вершины. Для графа, для
которого не определен вес
его ребер, расстояние определяется в
виде числа ребер.

Радиус
графа – минимальный эксцентриситет
вершин, а диаметр
графа – максимальный эксцентриситет
вершин.

Центр
графа образуют вершины, у которых
эксцентриситет равен радиусу. Центр
графа может состоять из одной, нескольких
или всех вершин графа.

Периферийные
вершины имеют эксцентриситет, равный
диаметру.

Простая цепь с
длиной, равной диаметру графа, называется
диаметральной.

Теорема 12.1.
В связном графе диаметр не больше ранга
его матрицы смежности.

Теорема 12.2.
(Жордана) Каждое дерево имеет центр,
состоящий из одной или двух смежных
вершин.

Теорема 12.3.
Если диаметр дерева четный, то дерево
имеет единственный центр, и все
диаметральные цепи проходят через него,
если диаметр нечетный, то центров два
и все диаметральные цепи содержат ребро,
их соединяющее.

Очевидно практическое
значение центра графа. Если, например,
речь идет о графе дорог с вершинами-городами,
то в математическом центре целесообразно
размещать административный центр,
складские помещения и т.п. Этот же подход
можно применять и для взвешенного графа,
где расстояния – это веса ребер. В
качестве веса можно брать евклидовое
расстояние, время или стоимость
передвижения между пунктами.

Пример 12.5.
Найти радиус, диаметр и центр графа,
изображенного на рис. 12.1.

Решение.
В данной задаче удобно использовать
матрицу
расстояний
S.
Элемент этой квадратной симметричной
матрицы
равен расстоянию между вершинойi
и вершиной j.
Для графа, показанного на рис. 12.1, матрица
расстояний имеет следующий вид:

. (12.2)

Вычислим
эксцентриситет
каждой вершины. Эту величину можно
определить как максимальный элемент
соответствующего столбца матрицы
расстояний (или строки – поскольку
матрицаS
симметрична).
Получаем

1

2

3

4

5

3

2

3

2

2

Радиус графа r
– минимальный эксцентриситет вершин.
В данном случае r
= 2. Такой эксцентриситет имеют вершины
№ 2, № 4 и № 5. Эти вершины образуют центр
графа. Диаметр графа d
– максимальный эксцентриситет вершин.
В данном случае d
= 3. Такой эксцентриситет имеют вершины
№ 1 и № 3, это периферия графа. В
исследованном графе вершины оказались
либо центральными, либо периферийными.
В графах большего порядка существуют
и другие вершины.

Эксцентриситеты
вершин небольшого графа легко вычислять
непосредственным подсчетом по рисунку.
Однако не всегда граф задан своим
рисунком. Кроме того, граф может иметь
большой размер. Поэтому необходим другой
способ решения предыдущей задачи.
Известна следующая теорема.

Теорема
12.4.
Пусть
– матрица смежности графа
G
без петель и
,
где.
Тогдаравно числу маршрутов длины
k
от вершины
к вершине.

Решение задач
теории графов с помощью различных
преобразований матрицы смежности
называют алгебраическим
методом
.

Пример 12.6.
Найти матрицу расстояний графа,
изображенного на рис. 12.1, алгебраическим
методом.

Решение.
Матрица смежности данного графа равна:

.

Будем заполнять
матрицу расстояний, рассматривая степени
матрицы смежности. Единицы матрицы
смежности показывают пары вершин,
расстояние между которыми равно единице
(т.е. они соединены одним ребром).

.

Диагональные
элементы матрицы расстояний – нули.
Умножаем матрицу смежности на себя:

.

Согласно теореме
между вершинами 2 и 3, 1 и 4 и т.д. имеется
некоторое число маршрутов длиной 2
(поскольку степень матрицы равна двум).
Число маршрутов здесь не используется,
важен сам факт наличия маршрута и его
длина, на что и указывает ненулевой
элемент степени матрицы, не совпадающий
с элементом, отмеченным при вычислении
маршрута меньшей длины. Проставляем 2
в незаполненные элементы матрицы
расстояний и получаем следующее
приближение:

.

Осталось неизвестным
расстояние между вершинами 1 и 3. Будем
умножать матрицу смежности

саму на себя до тех пор, пока в матрице


не появится ненулевой элемент
.
Тогда соответствующий элемент матрицы
расстояний равен степени матрицы
смежности:
.
На следующем шаге получаем

,

следовательно,
,
и окончательно

.

Полученная матрица
совпадает с матрицей расстояний S
(12.2), найденной непосредственными
вычислениями по рисунку.

    1. Эйлерова цепь

Маршрут в неографе,
в котором все ребра разные, называется
цепью.
Цепь в графе называется эйлеровой,
если она содержит все ребра и все вершины
графа.

Рис. 12.4. Схема
Кенигсбергских мостов

Теория графов
многократно переоткрывалась разными
авторами при решении различных прикладных
задач. В их ряду – знаменитый математик
Леонард Эйлер (1707-1783). К созданию теории
графов его подтолкнула задача о
Кенигсберских мостах, которую он решил
в 1736 году. По условию задачи требовалось
пройти по всем семи мостам города
Кенигсберга через реку Преголь по одному
разу и вернуться к исходной точке. На
рис. 12.4 показана схема этих мостов (один
из них соединяет между собой два острова,
а остальные – острова с берегами). Этой
схеме соответствует приведенный на
следующем рисунке мультиграф с четырьмя
вершинами.

Рис. 12.5

Эйлер решил задачу
о Кенигсбергских мостах в отрицательном
смысле. Он доказал, что данная задача
не имеет решения. Для этого ему пришлось
доказать следующую теорему.

Теорема 12.5
(Эйлера).
Мультиграф обладает эйлеровой цепью
тогда и только тогда, когда он связен и
число вершин нечетной степени равно 0
или 2.

Вершины нечетной
степени в этой теореме, очевидно, являются
началом и концом цепи. Если таких вершин
нет, то эйлерова цепь становится эйлеровым
циклом
.
Граф, обладающий эйлеровым циклом,
называется эйлеровым.
Если граф имеет эйлерову цепь, но не
обладает эйлеровым циклом (число вершин
нечетной степени равно 2), то он называется
полуэйлеровым
графом.

Предположим, что
граф имеет эйлеров цикл. Двигаясь по
нему, будем подсчитывать степени вершин,
полагая их до начала прохождения
нулевыми. Прохождение каждой вершины
вносит 2 в степень этой вершины. Поскольку
эйлеров цикл содержит все ребра, то
когда обход будет закончен, будут учтены
все ребра, а степени вершин – четные.

Все четыре вершины
мультиграфа, показанного на рис. 12.5,
имеют нечетные степени. Поэтому этот
граф не обладает эйлеровым циклом, а
задача о Кенигсбергских мостах не имеет
решения.

Рассмотрим для
сравнения граф, обладающий эйлеровой
цепью. В графе на рис. 12.6 только две
вершины имеют нечетную степень,
следовательно, эйлерова цепь есть.

Рис. 12.6

Цепей может быть
несколько. Например, граф на рис. 12.6
имеет две эйлеровы цепи: 1-2-3-4-1-3 и
1-2-3-1-4-3.

    1. Реберный граф

Рассмотрим два
графа G
и L(G).
Граф G
имеет произвольную форму, а вершины
графа L(G)
расположены на ребрах графа G.
В этом случае граф L(G)
называется реберным
графом
по
отношению к графу G.

Английское название
реберного графа – line
graph,
отсюда и обозначение графа – L(G).
На рис. 12.7 показан реберный граф (он
выделен жирными линиями), построенный
для графа с рис. 12.1.

Рис. 12.7. Реберный
граф

Теорема 12.6.
Если
– степенная последовательность (
n,
m)
графа
G,
то
L(G)
является (
m,
)-графом,
где

. (12.3)

Для графа G,
показанного на рис. 12.7 (и рис. 12.1), его
степенная последовательность: 1-3-2-3-3.
Поэтому

.

    1. Раскраска графа,
      хроматический полином

Предположим, что
перед нами стоит задача: раскрасить
карту мира так, чтобы каждая страна
имела свой собственный цвет. Поскольку
на свете существует несколько сотен
государств, то, естественно, потребуется
достаточно много разных красок.

Упростим задачу.
Будем использовать меньшее количество
красок, но при этом не будем допускать,
чтобы соседние страны, имеющие общие
границы, были окрашены в один цвет.
Возникает вопрос: какое минимальное
количество красок требуется, чтобы
удовлетворить этому условию?

Ответить на этот
вопрос можно с помощью теории графов.
Для этого нужно представить карту мира
в виде графа, каждая вершина которого
соответствует отдельной стране, а ребро
между смежными вершинами соответствует
наличию между странами общей границы.

Произвольная
функция

на множестве вершин графа называется
раскраской
графа. Раскраска называется правильной,
если

для любых смежных вершин
и.
Минимальное числоk,
при котором граф G
является k-раскрашиваемым
называется хроматическим
числом

графа
.

Граф называется
пустым,
если в нем удалены все ребра и вершины
изолированы друг от друга. Граф называется
полным,
если в нем нельзя добавить новое ребро,
не добавив при этом одновременно новую
вершину.

Теорема 12.7
(Брукса).

Для любого графа
G,
не являющегося полным,

,
еслимаксимальная
из степеней вершин графа
.

Для определения
количества способов раскраски графа в
x
цветов, необходимо составить хроматический
полином

P(G,
x).
Значение полинома при некотором
конкретном
равно числу правильных раскрасок графа
вцветов.

Существует лемма,
утверждающая, что хроматический
полином графа имеет вид

,(12.4)

где
– граф, полученный из
G
добавлением ребра (
u,
v),
а граф
получается из
G
отождествлением вершин
u
и
v.

Другой вариант
леммы:

, (12.5)

где
– граф, полученный из
G
удалением ребра (
u,
v),
а граф
получается из
G
отождествлением вершин
u
и
v.

Операцию
отождествления вершин u
и
v
называют также стягиванием ребра (u,
v).

Оба варианта леммы
составляют основу для хроматической
редукции графа (reduction
– «сокращение» на английском).
Хроматическая редукция графа –
представление графа в виде нескольких
пустых или полных графов, сумма
хроматических полиномов которых равна
хроматическому полиному графа. Очевидно,
что хроматический полином пустого графа
равен(каждая вершина может быть раскрашена
независимо от других), а для полного
графа.
Последнее выражение называютфакториальной
степенью

переменной x:
.

Разложения по
пустым и полным графам связаны.
Факториальную степень можно представить
в виде полинома:

, (12.6)

где
– числа Стирлинга первого рода. И
наоборот, степеньможно выразить через факториальные
степени:

, (12.7)

где
– числа Стирлинга второго рода, обладающие
следующими свойствами:

при
, (12.8)

при
,при.

При получении
хроматического полинома могут быть
полезны следующие теоремы.

Теорема 12.8.
Коэффициенты хроматического полинома
составляют знакопеременную
последовательность
.

Теорема 12.9.
Абсолютная величина второго коэффициента
хроматического полинома равна числу
ребер графа.

Теорема 12.10.
Наименьшее число
i,
для которого отличен от нуля коэффициент
при


в хроматическом полиноме графа
G,
равно числу компонент связности графа
G.

Кроме вершинной
раскраски, существует еще реберная
раскраска и раскраска граней.

Пример 12.7.
Найти хроматический полином графа,
показанного на рис. 12.8.

Рис. 12.8

Решение.
В зависимости от числа ребер графа можно
использовать разложение (12.4) или (12.5).
Если граф почти полный, то, добавив
несколько ребер по разложению (12.4),
получим хроматический полином в виде
суммы факториальных степеней. Если же
ребер мало и для получения пустого графа
требуется удалить только несколько
ребер, то следует использовать разложение
(12.5) с удалением ребер. Такие действия
называются хроматической редукцией.

1. Хроматическая
редукция по пустым графам
.
Воспользуемся вначале леммой (12.5). Удаляя
ребра и отождествляя соответствующие
вершины (стягивая ребра), сведем исходный
граф к пустым графам. Сначала разложим
граф на два, убрав, а затем стянув ребро
1-3. Выполненное действие запишем в виде
условного равенства:

Здесь
операция вычитания относится не к самому
графу, а к его хроматическому полиному.
Таким образом, последнее равенство
означает, что
.
Для сокращения записи обозначениеP(…)
будем опускать. Далее разложим каждый
из графов

и
,
пользуясь той же леммой.

Приведем подобные
члены:

(12.9)

В итоге получим
искомый хроматический полином:

. (12.10)

Разложение (12.9)
называется хроматической редукцией
графа по пустым графам.

Очевидно, что
результат соответствует утверждениям
теорем 12.8-12.10. Коэффициенты в (12.10) образуют
знакопеременную последовательность,
а коэффициент при
равен четырем – числу ребер. Наименьшая
степеньx
в полиноме равна 1, т.е. числу компонент
связности графа.

2. Хроматическая
редукция по полным графам
.
Добавив к изображенному на рис. 12.8 графу
ребро 1–4, получим граф с большим числом
ребер. Затем в исходном графе отождествим
вершины 1 и 4. В результате получим два
графа.

Отождествление
вершин приводит к уменьшению порядка
и иногда размера графа. Второй граф –
это полный граф
,
его преобразовывать больше не требуется.
К первому графу добавим ребро 1–2 и
отождествим вершины 1 и 2:

В итоге получим

(12.11)

Хроматический
полином примет вид

(12.12)

Разложение (12.11)
называется хроматической редукцией
графа по полным графам.

Оба способа дали
один результат, и из редукции по полным
графам легко получить редукцию по
пустым. Для этого достаточно раскрыть
скобки и привести подобные члены, как
в (12.12). Однако обратное действие не
очевидно. Для того чтобы полином
,
полученный из пустых графов, выразить
в виде суммы факториальных степеней,
необходимы числа Стирлинга 2-го рода.
Согласно рекуррентным формулам (12.8)
имеем следующие числа:

,

,

,

.

Пользуясь (12.7) и
найденными числами Стирлинга 2-го рода,
получим

,

,

.

Произведем
преобразование хроматического полинома:

Хроматическое
число
графа лучше всего получить, разложив
хроматический полином на множители:

.

Минимальное
натуральное число x,
при котором
не обращается в нуль, равно 3. Отсюда
следует.
Так как максимальная степень вершин
графа,
выполняется оценка.

    1. Ранг-полином
      графа

Ранг графа
определяется как
,
гдеn
– число вершин, k
– число компонент связности графа.
Коранг графа, или цикломатический ранг,
есть
,
гдеm
– число ребер.

Ранг-полином графа
G
имеет вид

,

где
– ранг графаG
, а
– корангостовного
(т.е. включающего в себя все вершины
графа) подграфа H,
а
– его ранг. Суммирование ведется по
всем остовным подграфам графаG.

Ранг полином
служит для анализа множества остовных
подграфов. Так, например, коэффициент
при
весть число подграфов размераk,
а значение
равно числу подграфов (включая
несобственный подграф), ранг которых
равен рангу самого графа.

Пример
12.8.
Найти
ранг-полином графа, изображенного на
рис. 12.8.

Решение.
Найдем все 16 остовных подграфов графа
G
(рис. 12.9). Множество представим в виде
четырех графов размера 1 (т.е. с одним
ребром), шести графов размера 2, четырех
графов размера 3 и двух несобственных
графов (пустой граф и граф G).

Рис. 12.9

Учитывая, что ранг
графа равен 3, получаем сумму:

    1. Циклы

Маршрут, в котором
начало и конец совпадают, – циклический.
Циклический маршрут называется циклом,
если он – цепь.

Остовом
графа G
называется граф, не содержащий циклов
и состоящий из ребер графа G
и всех его вершин. Остов графа определяется
неоднозначно.

Ребра графа, не
входящие в остов, называются хордами.
Цикл, получающийся при добавлении к
остову графа его хорды, называется
фундаментальным
относительно
этой хорды.

Теорема 12.11.
Число ребер неографа, которые необходимо
удалить для получения остова, не зависит
от последовательности их удаления и
равно цикломатическому рангу графа.

Пример 12.8.
По заданной матрице смежности:

,

определить число
циклов длины 3 ()
и длины 4 ().
Записатьматрицу
фундаментальных циклов
.

Решение.
Матрица смежности данного графа
симметричная, поэтому ей соответствует
неориентированный граф. Сумма ненулевых
элементов матрицы равна 12, следовательно,
по лемме о рукопожатиях в графе 6 ребер.
Построим этот граф (рис. 12.10). Очевидно,
в нем два цикла (3–4–5 и 1–3–5) длиной 3 и
один цикл (1–3–4–5) длиной 4. В данной
задаче решение получено прямым подсчетом
по изображению графа. Для более сложных
случаев существует алгоритм решения
задачи по матрице смежности.

Известно, что след
(trace)
матрицы смежности, возведенный в k
степень, равен числу циклических
маршрутов длины k
(см. теорему 12.4). Это число включает в
себя и искомое число циклов. Цикл
отличается от циклического маршрута
тем, что в нем не повторяются ребра.
Кроме того, предполагается, что искомые
циклы не помечены, а в след матрицы
входят именно помеченные маршруты.

Рис. 12.10

Непомеченных
циклов длиной 3 в 6 раз меньше, чем
помеченных, так как каждый помеченный
цикл может отличаться началом (а их в
данном случае три) и двумя направлениями
обхода (по и против часовой стрелки).
Возведем заданную матрицу смежности в
третью степень:

,

и получим

.

Поскольку
циклических маршрутов длиной 3, отличных
от циклов длиной 3, не существует,
найденное число и есть ответ в поставленной
задаче.

С циклами длиной
4 немного сложнее. В след четвертой
степени матрицы смежности графа

,

входят не только
циклы, но и циклические маршруты с
двойным и четырехкратным прохождением
ребер. Обозначим количество таких
маршрутов через
исоответственно. Очевидно, число маршрутов
с четырехкратным прохождением одного
ребра для вершиныравно степени этой вершины:.
Число маршрутов с двукратным прохождением
ребра складывается из числас висячей вершинойи числамаршрутов с вершинойв центре.

Легко заметить,
что
.
Числозависит от степеней вершин, соседних с:

,

где
– ребро, инцидентное вершинамi
и k.

Для графа на рис.
12.10 получим

,

,

,

.

С учетом того, что
непомеченных циклов длиной 4 в 8 раз
меньше, получим

.

После преобразований
формула примет вид

.

Для нахождения
матрицы фундаментальных циклов
пронумеруем ребра графа, начиная
нумерацию с хорд, как показано на рис.
12.11 (а).

Рис. 12.11

Двум хордам, 1 и 2,
соответствуют два фундаментальных
цикла: 1–4–5 и 2–4–6 (рис. 12.11 (б и в)).
Матрица фундаментальных циклов имеет
две строки (число циклов) и шесть столбцов
(число ребер).

1

2

3

4

5

6

1

1

0

0

1

1

0

2

0

1

0

1

0

1

В первой строке
матрицы единицами отмечены столбцы с
номерами ребер, входящих в первый цикл,
а во второй строке – номера ребер из
второго цикла.

Задача B. Радиус дерева

Условие

Деревом называется связный неориентированный граф без циклов. Для заданного
дерева требуется найти радиус.

Напишите программу, принимающую описание дерева и выводящую радиус дерева.

Формат входного файла

Входной файл содержит целое число N, за которым следует N − 1 описаний рёбер.
Описание ребра номер i содержит два целых числа ui vi — номера вершин,
которые соединены этим ребром.

Формат выходного файла

Выходной файл должен содержать единственное целое число — радиус дерева.

Ограничения

2 ≤ N ≤ 105, 1 ≤ ui, vi ≤ N.

Примеры тестов

Входной файл (input.txt) Выходной файл (output.txt)
1
2
1 2
1
2
3
1 2
1 3
1
3
7
1 4
2 3
2 4
2 5
4 6
4 7
2

Добавить комментарий