1 networkx初识
安装:
!pip install -i https://pypi.tuna.tsinghua.edu.cn/simple decorator==4.4.2
!pip install -i https://pypi.tuna.tsinghua.edu.cn/simple networkx
2 创建简单网络
# 导入库
import networkx as nx
import matplotlib.pyplot as plt
# 创建一个空图
G = nx.Graph()
# 向该图中添加节点和连边
G.add_nodes_from([1,2,3,4]) # 节点
G.add_edges_from([(1,2),(1,3),(2,3),(2,4), (1, 4)]) # 连边
# 可视化图
nx.draw(G, node_size=1000, node_color='red', with_labels=True)
# plt.savefig("fig1.png", dpi=300)
3 获取网络的邻接矩阵
# 无向无权
import networkx as nx
# 无向无权
G = nx.Graph()
G.add_nodes_from([1,2,3,4])
G.add_edges_from([(1,2),(1,3),(2,3),(2,4)])
# 系数矩阵
As = nx.adjacency_matrix(G)
print(As)
# 获取二维邻接矩阵
A = As.todense()
print(A)
# 有向无权
import networkx as nx
# 有向无权
G = nx.DiGraph()
G.add_nodes_from([1,2,3,4])
G.add_edges_from([(1,2),(2,3),(3,1),(2,4)])
As = nx.adjacency_matrix(G)
A = As.todense()
A
# 无向加权
import networkx as nx
# 无向加权
G = nx.Graph()
G.add_nodes_from([1,2,3,4])
G.add_weighted_edges_from([(1,2,2.0),(2,3,0.5),(3,1,1.0),(2,4,4.0)])
As = nx.adjacency_matrix(G)
A = As.todense()
A
# 无向带自环
import networkx as nx
# 无向带自环
G = nx.Graph()
G.add_nodes_from([1,2,3,4])
G.add_edges_from([(1,1),(1,2),(2,3),(3,1),(2,4),(4,4)])
As = nx.adjacency_matrix(G)
A = As.todense()
A
4 邻接矩阵
直接输入:
无向网络
import networkx as nx
import numpy as np
# 小规模矩阵
A = np.array([[0, 1, 1, 0],
[1, 0, 1, 1],
[1, 1, 0, 0],
[0, 1, 0, 0]], dtype=int)
G = nx.from_numpy_array(A)
nx.draw(G, with_labels=True)
有向网络:
import networkx as nx
import numpy as np
# 有向网络
DA = np.array([[0, 1, 1, 0],
[0, 0, 1, 1],
[1, 1, 0, 0],
[0, 0, 0, 0]], dtype=int)
DG = nx.from_numpy_array(DA, create_using=nx.DiGraph())
nx.draw(DG, with_labels=True)
从外部文件中读取:
import networkx as nx
import numpy as np
# 读取外部邻接矩阵数据
import pandas as pd
df = pd.read_csv("adjacency_matrix.csv", header=None, index_col=None)
G = nx.from_pandas_adjacency(df)
# 若为有向网络
# G = nx.from_pandas_adjacency(df, create_using=nx.DiGraph())
练习:
import networkx as nx
import numpy as np
# 读取外部邻接矩阵数据
import pandas as pd
# 创建一个空图
G = nx.Graph()
df = pd.read_excel("edges.xlsx", header=None, index_col=None)
G.add_nodes_from([1,2,3,4]) # 节点
df = np.array(df)
G.add_edges_from(df)
# 若为有向网络
# G = nx.from_pandas_adjacency(df, create_using=nx.DiGraph())
nx.draw(G, node_size=700, node_color='green', with_labels=True)
5 度、平均度以及度分布
- 无向无权网络
import networkx as nx
import numpy as np
# 创建空图
G = nx.Graph()
# 添加节点
G.add_nodes_from([1,2,3,4])
# 添加边
G.add_edges_from([(1,2),(2,3),(2,4),(3,4)])
# 获取网络G的度
d = dict(nx.degree(G))
print(d)
# 获取网络G的平均度
print("平均度为:", 2*len(G.edges())/len(G.nodes))
# 或采用如下方式
print("平均度为:", sum(d.values())/len(G.nodes))
# 获取度值出现的频数:返回所有位于区间[0, dmax]的度值的频率列表
nx.degree_histogram(G)
# 绘制分布直方图
# 导入绘图库
import matplotlib.pyplot as plt
x = list(range(max(d.values())+1))
y = [i/len(G.nodes) for i in nx.degree_histogram(G)]
print(x)
print(y)
plt.bar(x, y, width=0.5, color="blue")
plt.xlabel("$k$")
plt.ylabel("$p_k$")
plt.xlim([0,4])
- 无向加权网络
# 创建加权网络
WG = nx.Graph()
WG.add_weighted_edges_from([(0, 1, 3.0), (1, 2, 7.5), (0, 2, 1.5)])
# 获取网络G的度
wd = dict(nx.degree(WG, weight='weight'))
print(wd)
# 获取网络WG的平均加权度
print("平均加权度为:", sum(wd.values())/len(G.nodes))
- 有向网络
DG = nx.DiGraph()
# 添加节点
DG.add_nodes_from([1,2,3,4])
# 添加边
DG.add_edges_from([(1,2),(1,3),(2,3),(3,4),(4,3)])
nx.draw(DG, node_size=500, with_labels=True)
print("所有节点的入度为:", dict(DG.in_degree()))
print("所有节点的出度为:", dict(DG.out_degree()))
### 分别绘制入度和出度分布
di = dict(DG.in_degree())
print(di)
xi = list(range(max(di.values())+1))
yi = np.bincount(list(di.values()))
print(xi)
print(yi)
# 绘制入度频数分布直方图
plt.bar(xi, yi, width=0.5, color="red")
plt.xlabel("$k_{in}$")
plt.ylabel("$p(k_{in})$")
plt.xlim([-1,4])
# 出度分布与之类似
6 路径、距离、直径、效率和平均距离
- 无向无权网络
import networkx as nx
import numpy as np
# 创建空图
G = nx.Graph()
# 添加节点
G.add_nodes_from([1,2,3,4,5])
# 添加边
G.add_edges_from([(1,2),(2,3),(2,5),(3,4),(4,5)])
# 节点间的最短路径以及其长度
i, j = 1, 3
print(nx.shortest_path(G, i, j))
dij = nx.shortest_path_length(G, i, j)
dij
# 遍历所有节点间的最短路径长度
nodes = list(G.nodes())
for u in range(len(nodes)-1):
for v in range(u+1, len(nodes)):
i, j = nodes[u], nodes[v]
if nx.has_path(G, i, j):
dij = nx.shortest_path_length(G, i, j)
print("节点{}和{}之间的最短路径长度为{}".format(i, j, dij))
else:
print("节点{}和{}之间没有路径!".format(i, j))
# 直径:G是连通网络才可调用以下函数
print(nx.diameter(G))
# 平均最短路径长度
print(nx.average_shortest_path_length(G))
- 无向加权网络
# 创建加权网络
WG = nx.Graph()
WG.add_weighted_edges_from([(1,2,3.0),(2,3,1.5),
(2,5,2.5),(3,4,2.0),(4,5,4.0)])
# 加权网络节点间的最短路径长度
i, j = 1, 3
dij = nx.shortest_path_length(WG, i, j, weight='weight')
dij
扫描二维码关注公众号,回复:
14619939 查看本文章
# 不连通
Ga = nx.Graph()
Ga.add_nodes_from([1,2,3,4,5,6,7])
Ga.add_edges_from([(1,2),(1,3),(2,3),(4,7),(5,6),(5,7),(6,7)])
nx.draw(Ga, node_size=500, with_labels=True)
# 连通
Gb = nx.Graph()
Gb.add_nodes_from([1,2,3,4,5,6,7])
Gb.add_edges_from([(1,2),(1,3),(2,3),(2,4),(4,7),(5,6),(5,7),(6,7)])
nx.draw(Gb, node_size=500, with_labels=True)
print(nx.is_connected(Ga))
print(nx.is_connected(Gb))
7 网络的局部集聚系数、平均集聚系数以及全局集聚系数
import networkx as nx
import numpy as np
G = nx.Graph()
G.add_nodes_from([1,2,3,4,5,6,7])
G.add_edges_from([(1,2),(2,3),(2,4),(2,5),(4,5),(4,6),(4,7),(5,7)])
nx.draw(G, node_size=500, with_labels=True)
# 节点的局部集聚系数
# 返回字典格式,键为节点标签,值为对应的节点局部集聚系数
print(nx.clustering(G))
# 平均集聚系数
print(nx.average_clustering(G))
# 全局集聚系数
print(nx.transitivity(G))
# # 若图G为加权图,可增加权重参数来求解局部集聚系数和平均集聚系数
# nx.clustering(G, weight='weight')
# nx.average_clustering(G, weight='weight')
8 网络节点之间的独立路径数量
import networkx as nx
from networkx.algorithms import approximation as approx
# 创建一个简单无向图来展开演示
G = nx.Graph()
G.add_nodes_from([1,2,3,4,5,6,7,8])
G.add_edges_from([(1,2),(2,3),(2,4),(2,5),(4,5),(4,6),(4,7),(5,7)])
nx.draw(G, node_size=500, with_labels=True)
# 计算所有节点对之间的节点连通性:独立路径数量
print(approx.all_pairs_node_connectivity(G))
# 输出结果为一个字典:键为源节点,值也为一个字典,
# 该字典的键为目标approx.local_node_connectivity(G, 2, 4)节点,值为对应的独立路径数量。
# 该算法是一种快速逼近,给出了两个节点之间的节点独立路径实际数量的严格下界
# node_connectivity仅针对无向图
# 如果提供了源节点和目标节点,此函数等同于local_node_connectivity
approx.node_connectivity(G)
G2 = nx.octahedral_graph() # 柏拉图式的八面体图
nx.draw(G2, node_size=500, with_labels=True)
print(approx.all_pairs_node_connectivity(G2))
print(approx.node_connectivity(G2))
9 计算网络的相关性(匹配)系数、平均近邻度
匹配系数:
import networkx as nx
G = nx.Graph()
G.add_nodes_from([1,2,3,4,5,6,7])
G.add_edges_from([(1,2),(2,3),(2,4),(2,5),(4,5),(4,6),(4,7),(5,7)])
nx.draw(G, node_size=500, with_labels=True)
nx.degree_assortativity_coefficient(G)
nx.degree_pearson_correlation_coefficient(G)
平均近邻度:
# 平均近邻度
nx.average_neighbor_degree(G)
10 计算网络节点的中心性:度中心性、特征向量中心性、接近度中心性、介数中心性和PageRank中心性
度中心性:
特征向量中心性:
接近中心性:
import networkx as nx
G = nx.Graph()
G.add_nodes_from([1,2,3,4,5,6,7])
G.add_edges_from([(1,2),(2,3),(2,4),(2,5),(4,5),(4,6),(4,7),(5,7)])
nx.draw(G, node_size=500, with_labels=True)
# 度中心性
print(nx.degree_centrality(G))
# 遍历输出结果
DC = nx.degree_centrality(G)
for i in DC.keys():
print("节点{}的度中心性值为{:.4f}".format(i, DC[i]))
# 特征向量中心性
print(nx.eigenvector_centrality(G))
# 接近度中心性
print(nx.closeness_centrality(G))
# 节点介数中心性
print(nx.betweenness_centrality(G))
# 边介数中心性
print(nx.edge_betweenness_centrality(G))
# PageRank中心性
print(nx.pagerank(G))
11 获取网络的最大连通子图
import networkx as nx
G = nx.Graph()
G.add_nodes_from([1,2,3,4,5,6,7,8,9])
G.add_edges_from([(1,2),(2,3),(2,4),(2,5),(4,5),(4,6),(4,7),(5,7),(8,9)])
nx.draw(G, node_size=500, with_labels=True)
# 首先判断网络的连通性
print(nx.is_connected(G))
# 获取连通组件(子图)的数量
print(nx.number_connected_components(G))
# 获取所有连通子图:降序排序
Gcc = sorted(nx.connected_components(G), key=len, reverse=True)
# 获取最大连通子图
largest_cc = G.subgraph(Gcc[0])
nx.draw(largest_cc, node_size=500, with_labels=True)
nx.info(largest_cc)
# largest_cc.add_edge(3,6) # 连通子图不支持修改:NetworkXError: Frozen graph can't be modified
# 可以复制,在复制的图上修改
LCC = largest_cc.copy()
LCC.add_edge(3,6)
nx.draw(LCC, node_size=500, with_labels=True)
12 网络的k核
import networkx as nx
G = nx.Graph()
G.add_nodes_from([1,2,3,4,5,6,7])
G.add_edges_from([(1,2),(2,3),(2,4),(2,5),(4,5),(4,6),(4,7),(5,7)])
nx.draw(G, node_size=500, with_labels=True)
# 计算每个节点的K核值
print(nx.core_number(G))
# 获得度大于等于k的最大子图
k_subgraph = nx.k_core(G, k=2)
nx.draw(k_subgraph, node_size=500, with_labels=True)
13 连通网络的效率
import networkx as nx
G = nx.Graph()
G.add_nodes_from([1,2,3,4,5,6,7])
G.add_edges_from([(1,2),(2,3),(2,4),(2,5),(4,5),(4,6),(4,7),(5,7)])
nx.draw(G, node_size=500, with_labels=True)
# 计算指定节点对之间的效率:节点之间最短路径距离的倒数
print(nx.efficiency(G, 3, 7))
# 平均局部效率:网络节点的局部效率是该节点的邻居引起的子图的平均全局效率。
# 平均局部效率是每个节点的局部效率的平均值。
print(nx.local_efficiency(G))
# 全局效率:所有节点对之间效率的平均值
print(nx.global_efficiency(G))
14 针对图、节点以及连边的一些基本功能
import networkx as nx
G = nx.Graph()
G.add_nodes_from([1,2,3,4,5,6,7])
G.add_edges_from([(1,2),(2,3),(2,4),(2,5),(4,5),(4,6),(4,7),(5,7)])
nx.draw(G, node_size=500, with_labels=True)
# 获取图节点的度
print(dict(nx.degree(G)))
# 获取图的基本信息
print(nx.info(G))
# 获取指定节点的信息
print(nx.info(G, 4))
# 计算图连边密度
print(nx.density(G))
# 返回图节点标签
print(nx.nodes(G))
# 返回节点数量
print(nx.number_of_nodes(G))
# 获取指定节点的邻居
print(list(nx.neighbors(G, 2)))
# 获取指定节点的非邻居
print(list(nx.non_neighbors(G, 2)))
# 获取图中两个节点的公共邻居
print(list(nx.common_neighbors(G, 2, 4)))
# 返回所有连边
print(nx.edges(G))
# 返回连边数量
print(nx.number_of_edges(G))
图的边密度:图G=(V,E),其中V是图G的顶点集合,E是图G的边集。假设图G中的边数目为m,即|E|=m,顶点数目|V|=n,图的边密度p=2m/n(n-1)。
15 常见的网络生成器
import networkx as nx
# 生成包含n个节点的完全图(全连接图)
n = 10
G1 = nx.complete_graph(10)
pos = nx.circular_layout(G1)
nx.draw(G1, pos, node_size=500, node_color='red', with_labels=True)
# 生成包含n个节点的星型图
n = 10
G2 = nx.star_graph(n-1)
pos = nx.spring_layout(G2)
nx.draw(G2, pos, node_size=500, node_color='red', with_labels=True)
# 生成包含n个节点,连边概率为p的ER随机图
n, p = 20, 0.2
G3 = nx.erdos_renyi_graph(n, p)
nx.draw(G3, node_size=500, node_color='red', with_labels=True)
# 生成包含n个节点,重连概率为p的WS小世界网络
n, k, p = 20, 4, 0.2
# 当p=0时,便退化成了k近邻规则网络
G4 = nx.watts_strogatz_graph(n, k, p)
pos = nx.circular_layout(G4)
nx.draw(G4, pos, node_size=500, node_color='red', with_labels=True)
# 生成包含n个节点,参数m=2的BA无标度网络
n, m = 50, 2
G5 = nx.barabasi_albert_graph(n, m)
pos = nx.spring_layout(G5)
nx.draw(G5, pos, node_size=500, node_color='red', with_labels=False)
16 图的各种矩阵
import networkx as nx
# 生成包含n个节点,连边概率为p的ER随机图
n, p = 8, 0.5
G = nx.erdos_renyi_graph(n, p)
nx.draw(G, node_size=500, node_color='red', with_labels=True)
# 邻接矩阵
As = nx.adjacency_matrix(G)
print(As)
# 注意:对于networkx2.6以后的版本(如2.7,2.8)无法正常打印As,
# 会出现:FutureWarning: adjacency_matrix will return a
# scipy.sparse array instead of a matrix in Networkx 3.0.
# 但并不影响获取邻接矩阵。
# 转化成二维矩阵
print(As.todense())
# 返回G的关联矩阵:N*M,N为节点数,M为连边数
IM = nx.incidence_matrix(G)
IM.todense()
# 返回G的拉普拉斯矩阵
Ls = nx.laplacian_matrix(G)
# print(Ls)
L = Ls.todense() # L = D - A,D为节点度组成的对角矩阵,A为邻接矩阵
print(L)
# 返回G的标准化拉普拉斯矩阵
NLs = nx.normalized_laplacian_matrix(G)
NL = NLs.todense()
print(NL)
17 计算图的邻接矩阵的谱和拉普拉斯矩阵的谱(特征值)
import networkx as nx
import numpy as np
# 生成包含n个节点,连边概率为p的ER随机图
n, p = 8, 0.5
G = nx.erdos_renyi_graph(n, p)
nx.draw(G, node_size=500, node_color='red', with_labels=True)
# 计算邻接矩阵的特征值
print(np.real(nx.adjacency_spectrum(G)))
# 计算拉普拉斯矩阵的特征值:第一个特征值通常为0
print(np.real(nx.laplacian_spectrum(G)))
18 网络与其他数据之间的转换
import networkx as nx
# 将字典数据转化为网络
d = {
0: {
1: {
"weight": 1}, 2: {
"weight": 2}}, 1: {
2: {
"weight": 3.5}}}
G = nx.Graph(d)
# 或者
# G = nx.from_dict_of_dicts(d)
edge_width = nx.get_edge_attributes(G, "weight")
# print(width)
nx.draw(G, node_size=500, node_color='red', with_labels=True, width=list(edge_width.values()))
# 反过来把网络转换成字典数据
print(nx.to_dict_of_dicts(G))
# 其他转换格式使用类似
edgelist = nx.to_edgelist(G)
print(edgelist)
G = nx.from_edgelist(edgelist)
# 获取邻接矩阵:matrix格式
A = nx.to_numpy_matrix(G)
A
# 获取邻接矩阵:array格式
A = nx.to_numpy_array(G)
A
19 通过pandas库读取外部网络数据生成网络
import networkx as nx
import pandas as pd
df = pd.read_excel("edges.xlsx")
G = nx.from_pandas_edgelist(df, 'source', 'target','weight', create_using = nx.Graph())
# 若为有向图,create_using = nx.DiGraph()
# 若为无权无向网络则:G = nx.from_pandas_edgelist(df, 'source', 'target', create_using = nx.Graph())
edge_width = nx.get_edge_attributes(G, "weight")
nx.draw(G, node_size=500, node_color='red', with_labels=True, width=list(edge_width.values()))
# 读取外部邻接矩阵数据:见第04课:已知邻接矩阵A,生成A对应的网络
df = pd.read_csv("adjacency_matrix.csv", header=None, index_col=None)
G = nx.from_pandas_adjacency(df)
# 若为有向网络
# G = nx.from_pandas_adjacency(df, create_using=nx.DiGraph())
20 对网络节点重新编号
import networkx as nx
G = nx.path_graph(3)
sorted(G)
mapping = {
0: "a", 1: "b", 2: "c"}
H = nx.relabel_nodes(G, mapping)
sorted(H)
# 应用场景:假如你从网络获取了一个真实网络数据集,但其节点编号不连续,
# 此时,你可以将节点重新按照一定的顺序来编号
G = nx.Graph()
G.add_nodes_from([0,2,3,5,6,8]) # 节点不连续
G.add_edges_from([(0,2),(2,3),(2,5),(3,6),(5,8)])
nx.draw(G, node_size=500, node_color='red', with_labels=True)
# 重新编号为0~(len(G.nodes())-1)
mapping = dict(zip(G, range(len(G.nodes()))))
G = nx.relabel_nodes(G, mapping)
nx.draw(G, node_size=500, node_color='red', with_labels=True)
21 网络的读与写功能
import networkx as nx
G = nx.barabasi_albert_graph(10,2)
# 邻接表格式
# 将网络G保存为邻接表数据
nx.write_adjlist(G, "BA.adjlist")
# 读取外部邻接表数据生成网络
G = nx.read_adjlist("BA.adjlist", create_using=nx.Graph)
gexf格式(Gephi下的一种数据格式)
接下来,通过Gephi导出gexf格式数据,进而通过NetworkX读取
将Gephi下的图保存为gexf格式,其操作流程如下:
# 直接读取会出现如下错误:
G = nx.read_gexf("edges1.gexf")
# NetworkXError: No <graph> element in GEXF file.
# 改为:
# <gexf version="1.2" xmlns="http://www.gexf.net/1.2draft"
# xmlns:viz="http://www.gexf.net/1.2/viz"
# xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
# xsi:schemaLocation="http://www.gexf.net/1.2draft
# http://www.gexf.net/1.2draft/gexf.xsd">
Image(filename = './16.png', width=500, height=350)
# 更改后的数据命名为:edges.gexf
G = nx.read_gexf("edges.gexf")
nx.draw(G, node_size=500, node_color="red", with_labels=True)
# 将networkx图保存为gexf格式
# nx.write_gexf(G, "test.gexf")
# gml格式(Gephi下的一种数据格式):通过Gephi得到gml格式数据
G = nx.read_gml("edges.gml")
print(G.edges())
# 将networkx图保存为gml格式
# nx.write_gml(G, "test.gml")
22 网络可视化
初级:
import networkx as nx
G = nx.barabasi_albert_graph(20, 1)
nx.draw(G)
# 设置布局,节点大小,节点颜色,连边颜色,标签等
pos = nx.spring_layout(G)
nx.draw(G, pos, node_size=100, node_color="red")
# 当设置的属性较多时,可以将其保存在字典中,以**不定长参数传入
options = {
'pos': nx.spring_layout(G),
'node_size': 300,
'node_color': "red",
'edge_color': "gray",
'width': 1.0, # 连边粗细
'with_labels': True,
}
nx.draw(G, **options)
进阶:
import networkx as nx
# 无向加权图:自定义节点坐标(布局),适用于绘制小规模网络
# 创建一个无向加权图
G = nx.Graph()
nodes = [0,1,2,3,4,5,6,7]
edge_list = [(0,1,2),(0,2,8),(0,3,1),(1,2,6),
(1, 4, 1), (2, 3, 7), (2, 4, 5), (2, 5, 1),
(2,6,2),(3,6,9),(4,5,3),(4,7,8),
(5,6,4),(5,7,6),(6,7,3)]
G.add_nodes_from(nodes)
G.add_weighted_edges_from(edge_list)
# 自定义各个节点的坐标
pos = {
0: (-2,0), 1:(-1,1), 2:(-1,0), 3:(-1,-1),
4: (1,1), 5:(1,0), 6:(1,-1), 7:(2,0)}
nx.draw(G, pos, node_size=500, node_color="red", with_labels=True)
# 将连边标签设定为其权重值
e_labels = {
(0, 1):"2",(0, 2):"8",(0, 3):"1",(1, 2):"6",
(1, 4): "1", (2, 3): "7", (2, 4): "5", (2, 5): "1",
(2, 6):"2",(3,6):"9",(4, 5):"3",(4,7):"8",
(5, 6):"4",(5,7):"6",(6, 7):"3"}
nx.draw_networkx_edge_labels(G, pos, edge_labels=e_labels)
# 设置连边粗细与权重成正比
edgewidth = [G.get_edge_data(*e)['weight'] for e in G.edges()]
options = {
'pos': pos,
'node_size': 500,
'node_color': "red",
'edge_color': "gray",
'width': edgewidth,
'with_labels': True,
}
nx.draw(G, **options)
高阶:
import matplotlib.pyplot as plt
import networkx as nx
G = nx.barabasi_albert_graph(20,2)
# 绘制网络图,按度值大小设定节点大小和颜色
# 设置节点大小与度成正比
nodesize = [G.degree(i)*100 for i in G.nodes()]
node_colors = [G.degree(i) for i in G.nodes()]
options = {
'pos': nx.spring_layout(G),
'node_size': nodesize,
'node_color': node_colors,
'cmap': plt.cm.cool, # 设置节点colormap
'edge_color': "gray",
'with_labels': True,
}
nx.draw(G, **options)
plt.show()
import numpy as np
import matplotlib.pyplot as plt
import networkx as nx
# 参考:https://www.jb51.net/article/171825.htm
def color(value):
digit = list(map(str, range(10))) + list("ABCDEF")
if isinstance(value, tuple):
string = '#'
for i in value:
a1 = i // 16
a2 = i % 16
string += digit[a1] + digit[a2]
return string
elif isinstance(value, str):
a1 = digit.index(value[1]) * 16 + digit.index(value[2])
a2 = digit.index(value[3]) * 16 + digit.index(value[4])
a3 = digit.index(value[5]) * 16 + digit.index(value[6])
return (a1, a2, a3)
# 定义获取节点坐标的函数
def get_node_coordinates(G):
pos = {
}
x = nx.get_node_attributes(G, 'x')
y = nx.get_node_attributes(G, 'y')
for i in G.nodes():
ix = x[i]
iy = y[i]
pos[i] = (ix, iy) # 节点i的坐标
return pos
def get_node_color(G):
nodes_color = {
}
r = nx.get_node_attributes(G, 'r')
g = nx.get_node_attributes(G, 'g')
b = nx.get_node_attributes(G, 'b')
for i in G.nodes():
rgb_value = (r[i], g[i], b[i])
nodes_color[i] = color(rgb_value) # 节点i的颜色
return nodes_color
G = nx.read_graphml("example.graphml")
print(G.edges())
# for e in G.edges():
edge_weight = nx.get_edge_attributes(G, 'weight')
nom_edge_weight = np.array(list(edge_weight.values()))/5
pos_nodes = get_node_coordinates(G)
nodes_color = get_node_color(G)
node_degree = dict(G.degree())
nodesize = np.array(list(node_degree.values()))*10
# print(nodesize)
# print(pos)
# print(nodes_color)
options = {
'pos': pos_nodes,
'node_size': nodesize,
'node_color': nodes_color.values(),
'edge_color': "gray",
'with_labels': False,
'node_shape': "s",
'alpha': 0.8,
'width': nom_edge_weight,
}
nx.draw(G, **options)
plt.show()