Подтвердить что ты не робот

Как визуализировать большую сеть в R?

Сетевые визуализации становятся общепринятыми в науке на практике. Но по мере увеличения размеров сетей общие визуализации становятся менее полезными. Просто слишком много узлов/вершин и ссылок/ребер. Часто усилия по визуализации приводят к созданию "шариков".

Были предложены некоторые новые подходы к решению этой проблемы, например:

Я уверен, что есть еще много подходов. Таким образом, мой вопрос: Как преодолеть проблему волоса, т.е. как визуализировать большие сети с помощью R?

Вот какой код, который имитирует примерную сеть:

# Load packages
lapply(c("devtools", "sna", "intergraph", "igraph", "network"), install.packages)
library(devtools)
devtools::install_github(repo="ggally", username="ggobi")
lapply(c("sna", "intergraph", "GGally", "igraph", "network"), 
       require, character.only=T)

# Set up data
set.seed(123)
g <- barabasi.game(1000)

# Plot data
g.plot <- ggnet(g, mode = "fruchtermanreingold")
g.plot

enter image description here

Эти вопросы связаны с Визуализация непрямого графика, который слишком большой для GraphViz?. Однако здесь я ищу не общие рекомендации по программному обеспечению, а примеры (используя приведенные выше данные), которые помогают сделать хорошую визуализацию большой сети с помощью R (сопоставимо с примерами в этот поток: R: Scatterplot со слишком большим количеством точек).

4b9b3361

Ответ 1

Другой способ визуализации очень больших сетей - это BioFabric (www.BioFabric.org), который использует горизонтальные линии вместо точек для представления узлов. Затем отображаются края с использованием сегментов вертикальной линии. Быстрая демо-версия D3 этого метода показана по адресу: http://www.biofabric.org/gallery/pages/SuperQuickBioFabric.html.

BioFabric - это приложение Java, но простая версия R доступна по адресу: https://github.com/wjrl/RBioFabric.

Вот фрагмент кода R:

 # You need 'devtools':
 install.packages("devtools")
 library(devtools)

 # you need igraph:
 install.packages("igraph")
 library(igraph)

 # install and load 'RBioFabric' from GitHub
 install_github('RBioFabric',  username='wjrl')
 library(RBioFabric)

 #
 # This is the example provided in the question:
 #

 set.seed(123)
 bfGraph = barabasi.game(1000)

 # This example has 1000 nodes, just like the provided example, but it 
 # adds 6 edges in each step, making for an interesting shape; play
 # around with different values.

 # bfGraph = barabasi.game(1000, m=6, directed=FALSE)

 # Plot it up! For best results, make the PDF in the same
 # aspect ratio as the network, though a little extra height
 # covers the top labels. Given the size of the network,
 # a PDF width of 100 gives us good resolution.

 height <- vcount(bfGraph)
 width <- ecount(bfGraph)
 aspect <- height / width;
 plotWidth <- 100.0
 plotHeight <- plotWidth * (aspect * 1.2)
 pdf("myBioFabricOutput.pdf", width=plotWidth, height=plotHeight)
 bioFabric(bfGraph)
 dev.off()

Вот кадр из BioFabric версии данных, предоставленных экспертом, хотя более интересны сети, созданные со значениями m > 1. Вставка детализирует крупный план верхнего левого угла сети; node BF4 является наивысшей степенью node в сети, а макет по умолчанию - это поиск по ширине сети (игнорирование направлений кромки), начиная с этого node, с соседними узлами, пересекающимися в порядке убывания node степень. Обратите внимание, что мы можем сразу увидеть, что, например, около 60% node соседей BF4 имеют степень 1. Мы также можем видеть из строгой 45-градусной нижней границы, что эта сеть 1000- node имеет 999 ребер и является поэтому дерево.

BioFabric presentation of example data

Полное раскрытие: BioFabric - это инструмент, который я написал.

Ответ 2

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

enter image description here

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

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

Как построить hiveplot http://www.hiveplot.net/img/hiveplot-undirected-01.png

Тот факт, что метод детерминирован, интересен, поскольку он позволяет сравнивать разные сети, представляющие различные (но сопоставимые) системы. Например, вы можете сравнить два университета (при условии, что вы используете одни и те же атрибуты/меры для определения осей и положения). Он также позволяет описывать одну и ту же сеть различными способами, выбирая различные комбинации атрибутов/мер для генерации визуализации. Это рекомендуемый способ визуализации сети, фактически, благодаря так называемой панели улья.

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

Ответ 3

Я недавно занимался этой проблемой. В результате я придумал другое решение. Свернуть граф сообществами/кластерами. Этот подход аналогичен третьему варианту, описанному выше. Как предупреждение, этот подход будет лучше работать с неориентированными графами. Например:

library(igraph)

set.seed(123)
g <- barabasi.game(1000) %>%
  as.undirected()

#Choose your favorite algorithm to find communities.  The algorithm below is great for large networks but only works with undirected graphs
c_g <- fastgreedy.community(g)

#Collapse the graph by communities.  This insight is due to this post http://stackoverflow.com/questions/35000554/collapsing-graph-by-clusters-in-igraph/35000823#35000823

res_g <- simplify(contract(g, membership(c_g))) 

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

plot(g, margin = -.5)

введите описание изображения здесь

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

plot(r_g, margin = -.5)

введите описание изображения здесь

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

mem <- data.frame(vertices = 1:vcount(g), memeber = as.numeric(membership(c_g)))

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

Ответ 4

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