本程序将使用字典来构建有向无环图,然后遍历图将其转换为对应的Excel文件
最终结果如下:
代码:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
|
(py3) [root@ 7 - o - 1 py - dag] # cat test.py
from dag import DAG
dag = DAG()
dag.from_dict({ 'a' : [ 'b' , 'c' , 'e' ],
'b' : [ 'd' , 'g' ],
'c' : [ 'd' ],
'g' :[ 'i' ],
'i' :[],
'e' :[ 'gh' , 'ox' , 'wer' ],
'gh' :[],
'ox' :[],
'wer' :[],
'd' : []})
def generate_excel(dag, row_start,col,excel_file): #参数分别为有向无环图图、开始写入的行,开始写入列,以及文件名
workbook = xlsxwriter.Workbook(excel_file) #创建Excel文件
worksheet = workbook.add_worksheet( 'testsheet' ) #创建工作簿
#以下为部分格式的预定义(包含合并行格式,数字日期格式等)
merge_format = workbook.add_format({
'bold' : 1 ,
'border' : 1 ,
'align' : 'left' ,
'valign' : 'vcenter' })
cell_format = workbook.add_format({
'bold' : 1 ,
'border' : 1 ,
'align' : 'top' ,
'valign' : 'left' })
date_format = workbook.add_format({
'bold' : 1 ,
'border' : 1 ,
'align' : 'top' ,
'valign' : 'left' ,
'num_format' : 'd mmmm yyyy' })
num_format = workbook.add_format({
'bold' : 1 ,
'border' : 1 ,
'align' : 'top' ,
'valign' : 'left' ,
'num_format' : '0.0000%' })
def get_node_leaves(node,ret = []): #用来返回一个节点的所有最终叶子结点
downs = dag.downstream(node) #先获取当前节点的下一级节点
if len (downs) < 1 : #如果无下一级节点将直接将此节点添加到列表
ret.append(node)
else : #负责循环递归,将所有叶子结点添加到列表
for inner_node in downs:
get_node_leaves(inner_node,ret)
return ret #返回节点列表
def dag_visit(dag, node, r_idx,col):
if node not in all_leaves:
downstreams = dag.downstream(node)
node_leaves = len (get_node_leaves(node,[])) #获取所有叶子的个数,用来判断是否进行合并行操作
r_idx_end = r_idx + node_leaves - 1
if len (downstreams) = = 1 : #对于只有一个子节点的node应用write
worksheet.write(col + str (r_idx), node,cell_format)
else : #对于多余一个子节点的node应用merge_range
worksheet.merge_range(col + str (r_idx) + ':' + col + str (r_idx_end), node,merge_format)
col = chr ( ord (col) + 1 ) #列+1,开始进入子节点遍历
downstreams_len = len (downstreams)
if len (downstreams) > 0 :
row_next = r_idx
for downstream in downstreams:
subnode_leaves = len (get_node_leaves(downstream,[])) #获取当前节点的所有叶子用来为下一个节点的填充确定位移
if downstream in all_leaves:
subnode_leaves = 1
if col = = merge_to: #对于子节点为叶子并且跨度为1应用write
worksheet.write(col + str (row_next), downstream,cell_format)
else : #对于子节点为叶子结点但是跨度大于1应用merge_range
merge_rg = col + str (row_next) + ':' + merge_to + str (row_next)
worksheet.merge_range(merge_rg, downstream,merge_format)
else : #子节点非叶子结点进行递归遍历
dag_visit(dag, downstream, row_next,col)
#每访问一个子结点需要将row值增加方便下一个node正确填充,row的值是前一个结点的子节点个数
row_next + = subnode_leaves
else :
print (node)
head_node = dag.ind_nodes()[ 0 ]
all_leaves = dag.all_leaves()
dag_depth = dag.dag_depth(head_node, 0 )
merge_to = chr ( ord (col) + dag_depth) #对于合并列的终结列index
dag_visit(dag, head_node, row_start,col) #传递根节点进行遍历
workbook.close()
generate_excel(dag, 1 , 'A' , 'test.xlsx' )
|
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持服务器之家。
原文链接:https://blog.csdn.net/Lockey23/article/details/81254794