在R中正确绘制大型邻接矩阵

10
我有一个相当大但非常稀疏的邻接矩阵(500x500),我想要进行可视化呈现。在尝试找出最佳实现方式时,我发现了多个与R相关的资源,似乎类似于力导向图是最好的选择。其中最有帮助的是http://kateto.net/network-visualization上的网络可视化。虽然我以前从未使用过R,但它似乎具有许多对这种类型的可视化有用的功能。
我已经成功生成了下面的绘图,但是图像非常小,节点被堆叠在一起。

enter image description here

如果我将内容打印为PDF而不是PNG,则分辨率会略有提高,但我仍然遇到了堆叠问题。我的问题是,如何在R中正确绘制大型邻接矩阵以解决这些问题。

到目前为止,我的代码如下(最后几行是我尝试绘制数据的几种不同方式)。非常感谢任何提示。先行致谢。

为方便起见,我已将两个所引用的文件上传到我的GitHub上https://github.com/BStricklin/DataViz

plot.new()
library('igraph')
setwd("D:/Downloads/polnet2016/Data files")

nodes2 <- read.csv("nodes.csv", header=T, as.is=T)
links2 <- read.csv("nodeAdjacency.csv", header=T, row.names=1)

links2 <- as.matrix(links2)

head(nodes2)
head(links2)

net2 <- graph_from_incidence_matrix(links2)
net2 <- graph_from_adjacency_matrix(links2, mode = "undirected", weighted = TRUE)
net2 <- simplify(net2, remove.multiple = F, remove.loops = T) 

V(net2)$label <- nodes2$id

deg <- degree(net2, mode="all")
V(net2)$size <- deg*3

#plot(net2)
#plot(net2, edge.label=round(E(net2)$weight, 3))
layout <- layout.reingold.tilford(net2)
#plot.igraph(net2,vertex.size=3,layout=layout.lgl)
plot.igraph(net2,vertex.size=3,vertex.label.cex=.5,layout=layout.fruchterman.reingold(net2, niter=10000))

编辑:对于任何想知道我是如何做到这一点的人,我必须使用MATLAB并利用图形和绘图函数。它看起来与R图像差不多丑陋,但通过自定义节点和使用缩放功能,它足够好地工作了。不过,我仍然对如何在R中实现此操作感兴趣。


看到矩阵与图形的对比绘图会很有趣。https://en.wikipedia.org/wiki/Adjacency_matrix - Z boson
1
你是对的 @user20650,链接是http://kateto.net/network-visualization - Drofdarb
@Zboson 如果你访问我的 Github 页面,文件 nodeAdjacency.csv 就是所谓的图。不同之处在于矩阵是加权的,因此与你链接的页面上的简单填充框不同,矩阵中的数字代表连接强度。 - Drofdarb
一种选择是使用statnet包,并在gplot函数中设置displayisolates = FALSE。如果您坚持使用igraph,则可以设置一个阈值来绘制大于常数的边缘。 - monarque13
我会考虑使用例如networkD3制作交互式图表。相比静态图表,这些通常更有用,可以得出有用的信息。 - alan ocallaghan
3个回答

2

您可以从简化网络可视化的角度开始,删除未连接的顶点-即度数低于1的顶点:

net3 <- delete.vertices(net2, degree(net2)<1)

然后,您可以使用一种更适合大型网络的布局算法,例如 layout_with_graphopt,这是一种力导向算法,它允许设置“弹簧”的初始长度,这些弹簧会产生力,最终导致最终布局:

net.graphopt <- layout_with_graphopt(net3, charge = 0.009, mass = 50, spring.length = E(net3)$weight) 

最终,您可以在更大的绘图区域中绘制网络(如上面第一个答案所建议的),通过增加pdf()命令的高度和宽度来实现,具体如下:

pdf("graphopt.pdf", height = 14, width = 14)
plot.igraph(net3,vertex.size=2,vertex.label.cex=.5,layout=net.graphopt)
dev.off()

最终结果仍有些混乱,但至少避免了节点过多重叠:
使用igraph::layout_with_graphopt绘制的网络:

0

如果您打算使用网络作为表示方式,那么您需要优化图形布局算法的布局参数,例如Fruchterman-Reingold,以获得漂亮的布局。

另一种解决方案是使用另一种表示方式,如简单矩阵,请参见“使用R和ggplot2绘制邻接矩阵图”。

最后,您可以选择最大的组件并将其单独绘制。这是我通常采用的方法。


0

尝试将绘图区域扩大:

png("network_name.png", width = 15, height = 15, units = "in", res = 300)
plot.igraph(net2,vertex.size=3, 
vertex.label.cex=.5, 
layout=layout.fruchterman.reingold(net2, niter=10000)) 
dev.off()

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接