1. 先使用下面代码安装所必须的networkx numpy matplotlib的三个工具包
!pip install networkx numpy matplotlib
2. 安装完后,导入所需工具包,并且将matplotlib所画的图内嵌到jupyter中,并且设置中文字体等来正确显示汉字
- import networkx as nx # 图数据挖掘
- import numpy as np # 数据分析
- import random # 随机数
- import pandas as pd
-
- # 数据可视化
- import matplotlib.pyplot as plt
- %matplotlib inline
- plt.rcParams['font.sans-serif']=['SimHei'] # 用来正常显示中文标签
- plt.rcParams['axes.unicode_minus']=False # 用来正常显示负号
3. 在OpenKG下载四大名著人物关系知识图谱和OWL本体
4. 接着导入导入 csv 文件定义的有向图,保存三元组信息到df中
- # 导入 csv 文件定义的有向图
- df = pd.read_csv('data/三国演义/triples.csv')
运行后df信息如下:
5. 然后从DataFrame类型的df中提取两列数据,分别命名为head和tail。这两列数据应该是表示图中边的起始节点和终止节点的。然后使用zip函数将head和tail两列数据组合成一个新的列表edges,其中每个元素是一个元组,包含一对节点。接着创建一个有向图(DiGraph)对象G,使用add_edges_from方法将edges列表中的边添加到图G中。代码如下:
- edges = [edge for edge in zip(df['head'], df['tail'])]
-
- G = nx.DiGraph()
- G.add_edges_from(edges)
打印图的信息,可以发现有123个节点及144条边。
如下,每个节点的名称可以使用G.nodes打印及,len(G)能够打印出来节点的数量。
6. 使用networkx和matplotlib.pyplot可视化图
- # 可视化
- plt.figure(figsize=(15,14))
- pos = nx.spring_layout(G, iterations=3, seed=5) #设置为基于弹簧布局,迭代次数为3,次数越多,根据节点之间的相互作用力找到的节点位置越合理
- nx.draw(G, pos, with_labels=True)
- plt.show()
效果如下:
7. 接着计算每个节点PageRank的重要度
- pagerank = nx.pagerank(G, # NetworkX graph 有向图,如果是无向图则自动转为双向有向图
- alpha=0.85, # Damping Factor,阻尼系数,理解这个得理解谷歌矩阵,也就是明白算法本身才行
- personalization=None, # 是否开启Personalized PageRank,随机传送至指定节点集合的概率更高或更低
- max_iter=100, # 最大迭代次数
- tol=1e-06, # 判定收敛的误差
- nstart=None, # 每个节点初始PageRank值
- dangling=None, # Dead End死胡同节点
- )
需要跑一段时间,结果如下:
排序一波↓
8. 接着让那些PageRank值越大的节点,可视化时给与更大的可视化节点尺寸
参考文档:https://networkx.org/documentation/stable/auto_examples/drawing/plot_directed.html#sphx-glr-auto-examples-drawing-plot-directed-py
- # 节点尺寸
- node_sizes = (np.array(list(pagerank.values())) * 8000).astype(int)
9. 接着给每个节点、每条边颜色绘制,并且设置每个连接边的透明度等,透明度当然是越靠前的节点越不透明,因为越靠前的节点的PageRank越高,自然越重要,越不能透明。
- # 节点颜色
- M = G.number_of_edges()
- edge_colors = range(2, M + 2)
-
-
- plt.figure(figsize=(15,14))
-
- # 绘制节点
- nodes = nx.draw_networkx_nodes(G, pos, node_size=node_sizes, node_color=node_sizes)
-
- # 绘制连接
- edges = nx.draw_networkx_edges(
- G,
- pos,
- node_size=node_sizes, # 节点尺寸
- arrowstyle="->", # 箭头样式
- arrowsize=20, # 箭头尺寸
- edge_color=edge_colors, # 连接颜色
- edge_cmap=plt.cm.plasma,# 连接配色方案,可选:plt.cm.Blues
- width=4 # 连接线宽
- )
-
- # 设置每个连接的透明度
- edge_alphas = [(5 + i) / (M + 4) for i in range(M)]
- for i in range(M):
- edges[i].set_alpha(edge_alphas[i])
-
- # # 图例
- # pc = mpl.collections.PatchCollection(edges, cmap=cmap)
- # pc.set_array(edge_colors)
- # plt.colorbar(pc)
-
- ax = plt.gca()
- ax.set_axis_off()
- plt.show()
plt.show()的结果如下: