#python #networkx #bokeh #holoviews
#python #networkx #боке #holoviews
Вопрос:
итак, я пытаюсь раскрасить свои узлы в соответствии с категориями, скажем categories = ['a', 'b', 'c']
for comb in data:
edges.append((comb['comb'][0], comb['comb'][1], comb['count']))
graph = hv.Graph(edges, vdims='weight')
graph = layout_nodes(graph, layout=nx.layout.fruchterman_reingold_layout, kwargs={'weight': 'weight'})
nodes_array = graph.nodes.array()
for node in nodes_array:
(node) #add vdim to node here and set node_color to this vdim?
labels = hv.Labels(([i[0] for i in nodes_array], [i[1] for i in nodes_array], [i[2] for i in nodes_array]))
(graph.opts(width=800, height=800, node_color='weight')*labels.opts(text_font_size='8pt', text_color='blue'))
что мне нужно, так это способ сделать это, я полагаю, мне нужно установить категорию для каждого узла, каким-то образом определить его как vdim, а затем установить node_color для этого vdim?
Я видел другие вопросы о конкретных узлах и тому подобное, но я не думаю, что смогу определить узлы (включая положение), поскольку мне нужно fruchterman_reingold_layout
сделать это для меня.
(Бонус, если есть способ также изменить размер узла)
редактировать: Итак, я также попробовал добавить измерение через add_dimension
, как показано в документации здесь: http://holoviews.org/user_guide/Dimensioned_Containers.html
graph.nodes.add_dimension('weight', dim_pos=3, dim_val=['a'] * 457)
457 — это количество моих узлов, так что это правильно, но я получаю следующую ошибку: ValueError: kdims: list length must be between 3 and 3 (inclusive)
также я точно не знаю, что делать с результатом функции, я думаю, каким-то образом установить его как новые узлы?
Ответ №1:
Отвечая на мой собственный вопрос, я нашел способ добиться желаемого результата. Это скорее обходной путь, чем чистое решение, но оно работает, поэтому может быть полезным для других, пока не будет лучшего ответа.
from holoviews.element.graphs import layout_nodes
import random
G = hv.Graph([
('a', 'b', 3),
('a', 'c', 0.2),
('c', 'd', 0.1),
('c', 'e', 0.7),
('c', 'f', 5),
('a', 'd', 0.3)
], vdims=['weight'])
G = layout_nodes(G, layout=nx.layout.fruchterman_reingold_layout, kwargs={'weight': 'weight'})
nodes_array = G.nodes.array()
newNodes_array = []
for node in nodes_array:
newNodes_array.append((node[0], node[1], node[2], random.choice(['class1', 'class2', 'class3'])))
N = hv.Nodes(newNodes_array, vdims='class')
labels = hv.Labels(([i[0] for i in nodes_array], [i[1] for i in nodes_array], [i[2] for i in nodes_array]))
G*(N).opts(color = 'class', cmap='Set1')*labels
После G.nodes.array()
применения требуемого копируется nx.layout.fruchterman_reingold_layout
, поэтому затем можно добавить новое измерение к этим узлам и построить их вместе с графиком.
Вывод: