首页 > 解决方案 > 在 python networkx 中创建与主图具有相同边样式/宽度的节点类型子图

问题描述

我正在尝试基于我创建的代表项目团队数据网络的主图创建子图。节点是团队成员,边是它们之间的数据流

项目团队由不同的项目角色组成:项目经理、项目助理、工程师等。网络中的节点根据该节点的项目角色具有一定的颜色。

数据流知道某些频率(低、中、高、非常高)和值(低、中、高、非常高)。边缘具有基于数据流频率的特定宽度和基于数据流值的样式。

我的主图如下所示: 主图

现在我想创建一个子图,仅突出显示项目管理器(黄色节点)以及它们之间具有相同边缘宽度和样式的边缘。我设法创建了黄色节点的子图,但我不知道如何保持正确的边缘宽度和样式。这是我的两个结果:

选项 1:具有固定边宽 (5.0) 和样式(实心)的黄色节点的子图。问题是它没有显示任何关于频率/值的信息。

子图1

我使用代码:

Graph_C_PDM = C.subgraph(nodelist_PDM)
plt.figure(figsize=(35,35))
pos = nx.kamada_kawai_layout(C)
nx.draw(C, pos, with_labels=True, alpha=0.2, edges=edges_C, width=edge_frequency_C, style=edge_value_C, edge_color='black', node_color=node_colors_C, node_size=3000, font_size=25)
nx.draw(Graph_C_PDM, pos, with_labels=True, edges=edges_C, width=5, style='solid', edge_color='black', node_color='gold', node_size=3000, font_size=25)
plt.savefig('Graph_C_PDM.pdf')

选项2:带有边缘宽度的黄色节点的子图和主图的样式列表。问题是它显示了来自主图表列表的错误边缘宽度和样式。

子图2

我使用代码:

Graph_C_PDM = C.subgraph(nodelist_PDM)
plt.figure(figsize=(35,35))
pos = nx.kamada_kawai_layout(C)
nx.draw(C, pos, with_labels=True, alpha=0.2, edges=edges_C, width=edge_frequency_C, style=edge_value_C, edge_color='black', node_color=node_colors_C, node_size=3000, font_size=25)
nx.draw(Graph_C_PDM, pos, with_labels=True, edges=edges_C, width=edge_frequency_C, style=edge_value_C, edge_color='black', node_color='gold', node_size=3000, font_size=25)
plt.savefig('Graph_C_PDM.pdf')

我认为我应该创建两个单独的列表,仅捕获项目经理(黄色节点)之间边缘的边缘频率和边缘值。但我不知道我应该怎么做。

有人可以帮帮我吗?

完整代码:

#Project C
#step 3.1: Create the empty graph.
C = nx.Graph()
#step 3.2: Call edges from pandas dataframe and set edge attributes by associated dataframe columns.
C = nx.from_pandas_edgelist(df_C, source='source', target='target', edge_attr=['edge_frequency','edge_value', 'edge_weight'])
#step 3.3: Create list of edges.
edges_C =C.edges()
#print(edges_C)
#step 3.4: Create edge list with edge frequency values from each row in the edge list.
edge_frequency_C = [C[u][v]['edge_frequency'] for u,v in edges_C]
#step 3.5: Create list with 'edge value' values from each row in the edge list.
edge_value_C = [C[u][v]['edge_value'] for u,v in edges_C]
#step 3.6: Create list with 'edge weight' values from each row in the edge list.
edge_weight_C = [C[u][v]['edge_weight'] for u,v in edges_C]
# print(edge_frequency_C)
# print(edge_value_C)
# print(edge_weight_C)

#Project C
#step 4.1: Retrieve the node and role information from the csv dataframes for each row and applicable columns.
node_attributes_C = []
for index, rows in df_C.iterrows():
    source_attributes_C = [rows.source, rows.source_role, rows.source_color]
    target_attributes_C = [rows.target, rows.target_role, rows.target_color]
    node_attributes_C.append(source_attributes_C)
    node_attributes_C.append(target_attributes_C)
#print(node_attributes_C)
#step 4.2: Remove duplicates to create a list of unique nodes and their associated attribute.
new_node_attributes_C = []
for item in node_attributes_C:
    if item not in new_node_attributes_C:
        new_node_attributes_C.append(item)
node_attributes_C=new_node_attributes_C
#print(node_attributes_C)
#print(len(node_attributes_C))
#step 4.3: Transform list [] format into dictionary format {key:value} for setting node attributes.
dict_node_roles_C={item[0]:item[1] for item in node_attributes_C}
dict_node_colors_C={item[0]:item[2] for item in node_attributes_C}
#print(dict_node_attributes_C)
#step 4.4: Set node attributes from the created dictionary to the existing nodes in the network.
nx.set_node_attributes(C, dict_node_roles_C, 'Role')
nx.set_node_attributes(C, dict_node_colors_C, 'Color')
#print(C.nodes(data=True))

#Project C
# step 5.1: Create empty list for adding node colors.
node_colors_C = []
#step 5.2: Retrieve the node color from each row of the unique node list and add it to the color list.
for item in node_attributes_C:
    node_colors_C.append(item[2])
# print(node_colors_C)

#Project C
#step 6.1: Set the size of the plot figure being big enough to present the graph.
plt.figure(figsize=(35,35))
#step 6.2: Set the layout style of the graph, here the Kamada Kawai layout is choosen.
pos = nx.kamada_kawai_layout(C)
#step 6.3: Creating the graph including desired graph, node and edge settings.
Graph_C = (nx.draw(C, pos, with_labels=True,edgelist=edges_C, width=edge_frequency_C, style=edge_value_C, edge_color='black', node_color=node_colors_C, node_size=3000, font_size=25))
#step 6.4: Saving the graph as a PDF file.
plt.savefig('Graph_C.pdf')
#step 6.5: Visualizing the graph.
plt.show(Graph_C)

# Step 7: Creating the role specific nodelists. 
nodelist_PDM = []
for (u,v) in C.nodes(data=True):
    if v['Role'] == 'Project / Design management':
        nodelist_PDM.append(u)
print(nodelist_PDM)

# Step 8: Mapping the data sharing networks for specific roles in the project.
# Project / Design management
Graph_C_PDM = C.subgraph(nodelist_PDM)
plt.figure(figsize=(35,35))
pos = nx.kamada_kawai_layout(C)
nx.draw(C, pos, with_labels=True, alpha=0.2, edges=edges_C, width=edge_frequency_C, style=edge_value_C, edge_color='black', node_color=node_colors_C, node_size=3000, font_size=25)
nx.draw(Graph_C_PDM, pos, with_labels=True, edges=edges_C, width=edge_frequency_C, style=edge_value_C, edge_color='black', node_color='gold', node_size=3000, font_size=25)
plt.savefig('Graph_C_PDM.pdf')

标签: python-3.xattributesnetworkxgraph-theorysubgraph

解决方案


我认为我应该创建两个单独的列表,仅捕获项目经理(黄色节点)之间边缘的边缘频率和边缘值。但我不知道我应该怎么做。

您可以通过检查相应的边是否仅包含代表您的项目经理的节点来过滤您的边数据列表。例如:

edges_PDM = []
edge_frequency_PDM = []
edge_value_PDM = []
for ii, (a, b) in in enumerate(edges_C):
    if a in node_list_PDM and b in node_list_PDM:
        edges_PDM.append((a, b))
        edge_frequency_PDM.append(edge_frequency_C[ii])
        edge_value_PDM.append(edge_value_C[ii])

另一方面,这是一个问得很好的第一个问题。下一次,如果您还包括一些示例数据,那就太好了,这样任何试图回答您的问题的人都可以轻松确定答案是否真的产生了正确的结果。


推荐阅读