def incidents(self, node): """ overrides the incidents function of digraph, to maintain the nodes mapping @type node: Node @param node: the nodes of the neighbors """ if isinstance(node, Node): return [self.nodesMap[uid] for uid in digraph.incidents(self, node.uid)] else: return digraph.incidents(self, node)
def page_rank(self): '''计算有向图PR值 ''' # 初始化一些参量 digraph = self.digraph nodes = digraph.nodes() graph_size = len(nodes) if graph_size == 0: return {} # 将没有出链节点添加和其他所有节点(包括自己)连接边 for node in nodes: if len(digraph.neighbors(node))==0: for linkNode in nodes: digraph.add_edge((node, linkNode)) # 初始化PR值 PR = dict.fromkeys(nodes, 1/graph_size) damping_value = (1-self.damping_factor)/graph_size # 迭代 for i in range(self.max_iterations): change = 0 # 遍历每个节点,求解PR值 for node in nodes: rank = 0 for inciNode in digraph.incidents(node): rank += self.damping_factor*PR[inciNode]/len(digraph.neighbors(inciNode)) rank += damping_value change += abs(PR[node]-rank) PR[node]=rank # 判断是否终止 if change <= self.min_delta: flag = True break if flag: print("finished in %d iterations."%i) else: print("finished out of iterations") return PR