有没有一种有效的方法来计算python中常见邻居(CC)和优先附件(PA)的矩阵分数?我正在使用igraph来计算其他方法的得分矩阵,例如jaccard的系数(Graph.similarity_jaccard()),骰子(Graph.similarity_dice)和adamic / adar(Graph.similarity_inverse_log_weighted()),但我还没有找到任何函数计算CC和PA的得分矩阵。
目前我在做:
#Preferential attachment score between nodes i and j in a graph g
len(g.neighbors(i))*len(g.neighbors(j))
#Common neighbors score between nodes i and j in a graph g
len(g.neighbors(i) and g.neighbors(j))
但我必须为网络中的所有边缘(i,j)执行此操作,在我的情况下,这个边缘非常大。
如果有人知道任何生成我正在寻找的分数矩阵的数学矩阵运算,我也会很感激。
答案 0 :(得分:2)
igraph中没有直接的功能。但请注意,len(g.neighbors(i))
只是顶点 i 的度数,因此您可以调用g.degree()
,使用NumPy将其视为一维矩阵,然后将其与自己的转置相乘ST列向量乘以右边的行向量。这为您提供了优先附件得分矩阵:
from numpy import matrix
d = matrix(g.degree())
pref_score_matrix = d.T*d
使用矩阵表示法,常见的邻居得分比较棘手,如果你的图表真的很大,我也不会对矩阵进行操作(即使只有2000个顶点,你也会得到一个有400万个元素的矩阵)。我只是为列表中的所有可能值缓存g.neighbors(i)
的集合表示,然后使用它来计算公共邻居分数,因为集合可以有效地交叉:
neisets = [set(g.neighbors(i)) for i in xrange(g.vcount())]
for v1, v2 in g.get_edgelist():
common_neis = neisets[v1].intersection(neisets[v2])
print "%d --> %d: %d" % (v1, v2, len(common_neis))
如果你真的想坚持使用矩阵,你可以用 n 构造一个 n 矩阵,只用NumPy中的zeros
函数,然后用零组成零。循环顶点一次。获取顶点 v 的所有邻居,并注意 v 的邻居的任何对都有一个共同的邻居: v 本身:
from itertools import combinations
from numpy import zeros
n = g.vcount()
common_neis = zeros(n, n)
for v in xrange(g.vcount()):
neis = g.neighbors(v)
for u, w in combinations(neis, 2):
# v is a common neighbor of u and w
common_neis[u, w] += 1
common_neis[w, u] += 1