В настоящее время я следую совету Стива Йегге по подготовке к собеседованию по техническому программированию: http://steve-yegge.blogspot.com/2008/03/get-that-job-at-google.html
В своем разделе о графиках он утверждает:
Существует три основных способа представления графа в памяти (объекты и указатели, матрица и список смежности), и вам следует ознакомиться с каждым представлением и его плюсами и минусами.
Плюсы и минусы представлений матриц и списков смежности описаны в CLRS, но мне не удалось найти ресурс, который сравнивал бы их с представлением объекта.
Просто подумав об этом, я сам могу сделать некоторые выводы, но я хотел бы убедиться, что не пропустил что-то важное. Если бы кто-то мог описать это всесторонне или указать мне на ресурс, который делает это, я был бы очень признателен.
источник
Ответы:
объекты и указатели
Это просто базовые структуры данных, такие как hammar, о которых говорится в другом ответе,
Java
вы бы представили это с помощью классов, таких как ребра и вершины. Например, ребро соединяет две вершины и может быть направленным или неориентированным и может содержать вес. Вершина может иметь идентификатор, имя и т. Д. В большинстве случаев обе имеют дополнительные свойства. Таким образом, вы можете построить свой график с ними, напримерЭтот подход обычно используется для объектно-ориентированных реализаций, поскольку он более читабелен и удобен для объектно-ориентированных пользователей;).
матрица
Матрица - это простой двумерный массив. Предполагая, что у вас есть идентификаторы вершин, которые можно представить в виде массива int следующим образом:
Это обычно используется для плотных графов, где необходим индексный доступ. Этим вы можете представить неуправляемую и взвешенную структуру.
список смежности
Это просто микс простой структуры данных, я обычно реализую это с помощью файла
HashMap<Vertex, List<Vertex>>
. Аналогичный крест может бытьHashMultimap
в Гуаве.Этот подход хорош, потому что у вас есть O (1) (амортизированный) поиск вершин, и он возвращает мне список всех смежных вершин с этой конкретной вершиной, которую я требовал.
Это используется для представления разреженных графиков. Если вы подаете заявку в Google, вы должны знать, что веб-граф разреженный. Вы можете справиться с ними более масштабируемым образом, используя BigTable .
Да и кстати, вот очень хорошее резюме этого поста с модными картинками;)
источник
HashMap
( docs.oracle.com/javase/7/docs/api/java/util/HashMap.html ), в котором говорится:This implementation provides constant-time performance for the basic operations
= O (1) амортизировано.HashTable
использовании. Так что не нужно придираться к небольшим постоянным альфа-накладным расходам, которыми можно пренебречь.Объекты и указатели - это в основном то же самое, что и список смежности, по крайней мере, для целей сравнения алгоритмов, использующих эти представления.
Сравнить
с участием
В последнем случае вы можете легко составить список соседей на лету, если с ним проще работать, чем с именованными указателями.
источник
Преимущество представления объекта ( списка инцидентности ) состоит в том, что две смежные вершины имеют один и тот же экземпляр ребра. Это позволяет легко манипулировать данными ненаправленных кромок (длина, стоимость, поток или даже направление). Однако он использует дополнительную память для указателей.
источник
Еще один хороший ресурс: Khan Academy - «Представляющие графы».
Помимо списка смежности и матрицы смежности, они перечисляют «списки ребер» как третий тип представления графа. Список ребер можно интерпретировать как список «объектов ребер», подобных тем, что в ответе Томаса «объекты и указатели».
Преимущество: мы можем хранить больше информации о кромке (упомянутой Михалом)
Недостаток: это очень медленная структура данных для работы:
e = количество ребер
источник