在python igraph中选择簇和顶点的数量

2024-09-29 02:24:38 发布

您现在位置:Python中文网/ 问答频道 /正文

我有一个完整的加权图,如下图所示:

enter image description here

目标: 我的目标是能够使用python的iGraph实现来选择集群的数量和每个集群中的顶点数量

我目前所做的努力:

import igraph
import cairo
import numpy as np

# Import data (see below, I've included this file)
graph2 = igraph.Graph.Read_Ncol('10_graph.ncol')

# Assigns weights to weights1
weights1 = graph2.es["weight"]

# Converts it to undirected graph
graph2.to_undirected()

# 'graph2.to_undirected()' strips the graph of its weights
# so we restore them to the "weight" attribute after
graph2.es["weight"] = weights1

# Reduces the number of significant figures in each edge label
graph2.es["label"] = np.around(weights1, 2)

# Label all the vertices
graph2.vs["label"] = range(1, 11)

# Things I've tried: (uncomment only one at a time)
# Both return non-clustered graphs.
#community = graph2.community_spinglass(weights1)
community = graph2.community_leading_eigenvector(weights=graph2.es["weight"], clusters=3)
igraph.plot(community)

如果运行上述代码,您将得到上面的图像作为输出。我所包含的两个社区搜索算法的图像都是一样的。我已经注释掉了其中一个,所以如果您想使用另一个,请继续取消注释#community = graph2.community_spinglass(weights1)。在

问题:

  • 看起来没有一个图是按照我想要的方式聚集的。
    • 我传递weights=graph2.es["weight"],图中顶点对应的权重列表。在
    • 我还显式地将clusters=3传递给community_leading_eigenvector()
    • 我仍然没有得到任何基于这个图的边缘权重的聚类。在
    • 如何通过颜色或位置绘制适当的簇,或者如何使用iGraph处理簇的区分?
  • 我找不到任何关于如何选择每个簇中顶点数量的官方文档。
    • 是否有方法(甚至是环形交叉)来选择每个簇中的顶点数?它不必是精确的,而是近似的。

10_图形.ncol

这是我导入的.ncol文件以形成图形。在

10个_图形.ncol=

^{pr2}$

Tags: thetocommunityimport数量esgraphweight
1条回答
网友
1楼 · 发布于 2024-09-29 02:24:38

两种方法都只返回一个集群。这告诉我你的顶点之间没有明显的分离:它们只是一个大的纠结,所以没有合理的方法把它们分开。在

如果我编辑边权重使其具有清晰的分离,如下面的10_g2.ncol,那么聚类算法会对顶点进行分割。在

在firs,这并没有产生我所期望的群体。我在顶点集{0,1,2,3},{4,5,6},和{7,8,9}内设置高权重,在不同集合之间设置低权重。但是自旋玻璃将其分成{0,1,2,5,6},{3,4},和{7,8,9},而前导特征向量则将其分成{0,1,2,5,6}和{3,4,7,8,9}。在

这是因为to_undirected()改变了边的顺序,所以当你在这个操作之后重新分配边权重时,它会将它们与之前不同的边相关联。为了避免这种情况,您应该指示to_undirected保留边缘属性,例如

graph2.to_undirected(combine_edges="max")

保留每个边属性的最大值(如果相同顶点之间有多条定向边),或

^{pr2}$

只保留看到的第一个值。(在这种情况下,该方法应该是无关的,因为没有多条边。)

一旦您实际将图形分割成多个簇,默认的plot方法将通过颜色来区分它们。您还可以使用community.subgraph(i)来获得第ith集群的子图并绘制它。在

控制集群的数量呢?如您所知,前导特征值方法有一个表示所需集群数量的clusters参数,但它显然更像是一个指导原则而不是一个实际规则:给出clusters=3只会得到1个包含您的数据的集群,2个包含我的数据的集群。在

您可以使用返回VertexDendrogram而不是集群的方法(如“community_edge_betweenness”)来更精确地控制集群的数量。在

^{3}$

要获得一个包含n集群的集群,可以调用com3.as_clustering(n),这正好为我所有的测试提供了n集群。在

它们不一定是好的集群:

In [21]: print(com3.as_clustering(3))
Clustering with 10 elements and 3 clusters
[0] 0
[1] 1, 2, 3, 4, 5, 7, 8, 9
[2] 6

In [22]: print(com3.as_clustering(4))
Clustering with 10 elements and 4 clusters
[0] 0
[1] 1, 2, 3, 4, 5, 8, 9
[2] 6
[3] 7

In [23]: print(com3.as_clustering(5))
Clustering with 10 elements and 5 clusters
[0] 0
[1] 1, 3, 5
[2] 2, 4, 8, 9
[3] 6
[4] 7

In [24]: print(com3.as_clustering(6))
Clustering with 10 elements and 6 clusters
[0] 0
[1] 1, 3, 5
[2] 2, 8, 9
[3] 4
[4] 6
[5] 7

其他返回顶点树状图的方法是community_walktrap和{}。在IMO这个例子中,它们似乎都表现得更好

In [25]: com5 = graph2.community_walktrap(weights='weight')

In [26]: com6 = graph2.community_fastgreedy(weights='weight')

In [27]: print(com5.as_clustering(3))
Clustering with 10 elements and 3 clusters
[0] 0, 1, 2, 5, 6
[1] 3, 4
[2] 7, 8, 9

In [32]: print(com6.as_clustering(3))
Clustering with 10 elements and 3 clusters
[0] 0, 1, 2, 5, 6
[1] 3, 4
[2] 7, 8, 9

这是我使用的更为多样化的权重。在

10_g2.ncol:

0 1 0.91
0 2 0.92
0 3 0.93
0 4 0.04
0 5 0.05
0 6 0.06
0 7 0.07
0 8 0.08
0 9 0.09
1 2 0.94
1 3 0.95
1 4 0.14
1 5 0.15
1 6 0.16
1 7 0.17
1 8 0.18
1 9 0.19
2 3 0.96
2 4 0.01
2 5 0.02
2 6 0.03
2 7 0.04
2 8 0.05
2 9 0.06
3 4 0.01
3 5 0.01
3 6 0.01
3 7 0.01
3 8 0.01
3 9 0.01
4 5 0.97
4 6 0.92
4 7 0.05
4 8 0.04
4 9 0.08
5 6 0.98
5 7 0.12
5 8 0.08
5 9 0.08
6 7 0.07
6 8 0.06
6 9 0.06
7 8 0.98
7 9 0.95
8 9 0.98

相关问题 更多 >