• Identification of Key Nodes Based on Integrating of Global and Local Information论文


      之前使用PageRank提取关键结点的方法是计算每个结点的PageRank的值,然后提取top10%的结点作为关键结点。但是PageRank是从全局视角给网页排序,从而得到的每个结点的PageRank的值。

      这篇文章结合复杂网络的局部特征和全局特征,通过标准化每个节点的度和中间性中心性,利用节点之间的连接强度将它们整合在一起。最后根据计算的SDB的值来表示结点的重要性。SDB值越大,结点在维护连接方面的作用变得更加重要

    文章方法的主要思路就是计算SDB的值

    SDB的值的计算公式如下:

     ki表示第i个结点的度,kavg表示结点度的平均数;bi表示第i个结点的介中心性,bavg表示结点的平均介中心性;Sij表示连接强度

    其中ki(di)的计算如下:

     bi的计算:

    Sij的计算如下:

     N(i)和N(j)分别表示结点i和j的邻居数,ki和kj分别表示结点i和j的度.Sij=0表示结点i和j没有公共邻居,Sij=1表示结点i和j的邻居完全相同。

    实验部分的话就是主要选取几个指标进行对比的过程。下面给出复现代码:

    import math
    
    import pandas as pd
    
    import utils.generate_network as gennet
    import networkx as nx
    import numpy as np
    import os
    
    
    # 1.根据图文件生成graph
    def gen_network(file_name):
        """
        根据图结点文件生成图
        :param file_name:
        :return:
        """
        G = gennet.gen_network(file_name)
        return G
    
    
    # 2. 计算每个结点的度ki 和所有节点的平均度 kavg
    def compute_degree(G):
        """
        计算给定图中每个结点的度和平均度
        :param G:
        :return:
        """
        degree_list = nx.degree(G)
        degree_val = [gd[1] for gd in list(degree_list)]
        avg_degree = np.average(degree_val)
        degree_dict = {}
        for dl in degree_list:
            degree_dict[dl[0]] = dl[1]
        return degree_dict, avg_degree
    
    
    # 3. 计算每个结点的介中心性 betweenness bi 和平均值 bavg
    def compute_betweenness(G):
        """
        计算给定图中每个结点的介中心性
        :param G:
        :return:
        """
        # 介中心性
        betweenness = nx.betweenness_centrality(G, normalized=False)
        # 平均介中心性
        avg_betweenness = np.average(list(betweenness.values()))
        return betweenness, avg_betweenness
    
    
    # 4. 计算结点i,j 的连接强度 sij
    def compute_connectivity(G, degree_dict):
        """
        计算结点间的连接强度
        :param G: 图 networkx
        :param degree_dict: 结点度 {nodei: ki}
        sij = |N(i) ∩ N(j)| / √(ki * kj)
        :return:
        """
        nodes_list = list(G.nodes)
        node_num = len(nodes_list)
        # 每个结点与其他结点对应的连接性
        connectivity = {}
        for i in range(0, node_num):
            neighbor_i = list(G.neighbors(nodes_list[i]))
            ki = degree_dict.get(nodes_list[i])
            conn_i = {}
            for j in range(0, node_num):
                neighbor_ni = list(G.neighbors(nodes_list[j]))
                k_ni = degree_dict.get(nodes_list[j])
                # 邻居结点交集
                intersection = [ni for ni in neighbor_i if ni in neighbor_ni]
                # 求sij
                sij = len(intersection) / math.sqrt(ki * k_ni)
                conn_i[nodes_list[j]] = sij
            connectivity[nodes_list[i]] = conn_i
        return connectivity
    
    
    # 5. 计算SDB = sum(((ki/kavg + b/ bavg) + (1-sij) * (ki/kavg + b/ bavg)平方) j∈Neighbor(i)
    def compute_sdb(G, out_path):
        """
        计算SDB
        :param G: 图 networkx
        :param out_path: 计算结果输出文件
        :return:
        """
        # 计算度
        degree_dict, avg_degree = compute_degree(G)
        # 计算介中心性
        betweenness_dict, avg_betweenness = compute_betweenness(G)
        # 计算连接强度
        connectivity_dict = compute_connectivity(G, degree_dict)
        node_list = list(G.nodes)
        SDB = []
        for node in node_list:
            ki = degree_dict.get(node)
            bi = betweenness_dict.get(node)
            connectivity = connectivity_dict.get(node)
            node_neighbor = list(G.neighbors(node))
            SDBi = 0
            for nn in node_neighbor:
                tmp = (ki / avg_degree + bi / avg_betweenness)
                sij = connectivity.get(nn)
                curr_sbd = math.pow(tmp + (1 - sij) * tmp, 2)
                SDBi += curr_sbd
            SDB.append(SDBi)
        sdb_value = pd.DataFrame(columns=["Node", "SDB"])
        sdb_value["Node"] = node_list
        sdb_value["SDB"] = SDB
        # 按照SDB排序
        sdb_value.sort_values(by="SDB", inplace=True, ascending=False)
        # sdb_value.to_csv(out_path, index=False, encoding="utf8")
        return sdb_value
    
    
    def get_top_10_percent(sdb_file, out_file):
        """
        获取sdb值最大的前10%的结点list
        :param out_file:
        :param sdb_file:
        :return:
        """
        sdb_data = pd.read_csv(sdb_file)
        data_num = sdb_data.shape[0]
        top_10_percent_num = int(data_num * 0.1)
        top_10_percent_data = sdb_data.head(top_10_percent_num)
        # top_10_percent_node = top_10_percent_data["node"].values.tolist()
        top_10_percent_data.to_csv(out_file, index=False, encoding="utf8")
  • 相关阅读:
    循环播放音乐
    在发板实现24位jpg和bmp图片用手划动显示上一张与下一张图片
    AnsiIO
    PosixIO
    java3
    java2
    java1
    ios音乐播放器demo
    添加文章查看连接
    elementary os变成mac风(笔记)
  • 原文地址:https://www.cnblogs.com/syq816/p/16331339.html
Copyright © 2020-2023  润新知