染色问题解决的第一步也是最重要的一步就是把结点按度数从大到小排好序
从而找到邻接点最多的点,即邻接点使用不同颜色,从而着色更少的点,得到最小着色数
# graph 数据格式在下方
def matrix_graph(g, v_num):
"""生成二维矩阵"""
return [[1 if col in g[row] else 0 for col in range(v_num)] for row in range(v_num)]
def nodes_inorder_des(m, v_num):
"""将结点按度数降序排好"""
deg = {}
for v in range(v_num):
deg[v] = m[v].count(1)
return sorted(deg, key=deg.get, reverse=True)
def graph_color(m, n, v_num):
"""将节点按照染色颜色划分"""
painted = set()
res = list()
for v in n:
if v not in painted: # 每次找未着色的点
group = list([v]) # 保存相同颜色的结点
painted.add(v)
for v_other in range(v_num):
if m[v][v_other] == 0 and v_other not in painted: # v与v_other不邻接 and 其邻接点没有被染色
if all(m[v_group][v_other] == 0 for v_group in # v_other与同组节点不邻接
group[1:]): # 拷贝group,保持不变性,并且从新加入节点开始比较
painted.add(v_other)
group.append(v_other)
res.append(group)
if len(painted) == total_v_num:
break
return res
if __name__ == '__main__':
total_v_num = len(graph)
matrix = matrix_graph(graph, total_v_num)
# debug
# for row in matrix:
# print(row)
nodes = nodes_inorder_des(matrix, total_v_num)
# debug
# print(nodes)
res = graph_color(matrix, nodes, total_v_num)
print('染色情况:', res)
print('染色数:', len(res))
graph = {
0: [2, 5, 6],
1: [4, 7, 9],
2: [0, 3, 6],
3: [2, 4, 6, 8],
4: [1, 3, 8, 9],
5: [0, 6, 10, 11, 15],
6: [0, 2, 3, 5, 8, 10, 17, 18],
7: [1, 9, 14],
8: [3, 4, 6, 9, 12, 18, 19],
9: [1, 4, 7, 8, 12, 14, 16, 19, 20],
10: [5, 6, 15, 17],
11: [5, 13, 15],
12: [8, 9, 19],
13: [11, 15, 21],
14: [7, 9, 16, 22],
15: [5, 10, 11, 13, 17, 21, 26, 27],
16: [9, 14, 20, 22, 25, 29],
17: [6, 10, 15, 18, 26, 31, 32],
18: [6, 8, 17, 19, 23, 32],
19: [8, 9, 12, 18, 20, 23],
20: [9, 16, 19, 23, 25, 34],
21: [13, 15, 27, 28],
22: [14, 16, 24, 29, 30],
23: [18, 19, 20, 32, 34],
24: [22, 30, 41],
25: [16, 20, 29, 33, 34],
26: [15, 17, 27, 31, 35, 38, 40],
27: [15, 21, 26, 28, 35],
28: [21, 27, 35, 37],
29: [16, 22, 25, 30, 33, 42],
30: [22, 24, 29, 41, 42, 43],
31: [17, 26, 32, 40],
32: [17, 18, 23, 31, 34, 39, 40, 45],
33: [25, 29, 34, 42, 44],
34: [20, 23, 25, 32, 33, 36, 44],
35: [26, 27, 28, 37, 38, 46],
36: [34, 39, 44, 45, 48, 50],
37: [28, 35, 46, 47],
38: [26, 35, 40, 46, 49, 51],
39: [32, 36, 45],
40: [26, 31, 32, 38, 45, 49],
41: [24, 30, 43, 52],
42: [29, 30, 33, 43, 44, 53, 58, 60],
43: [30, 41, 42, 52, 53],
44: [33, 34, 36, 42, 50, 58, 59],
45: [32, 36, 39, 40, 48, 49, 56],
46: [35, 37, 38, 47, 51, 54, 55],
47: [37, 46, 54],
48: [36, 45, 50, 56, 62],
49: [38, 40, 45, 51, 56, 57],
50: [36, 44, 48, 59, 62, 63],
51: [38, 46, 49, 55, 57, 61],
52: [41, 43, 53, 64],
53: [42, 43, 52, 60, 64],
54: [46, 47, 55],
55: [46, 51, 54, 61],
56: [45, 48, 49, 57, 62, 65, 66],
57: [49, 51, 56, 61, 65],
58: [42, 44, 59, 60, 68, 69],
59: [44, 50, 58, 63, 69],
60: [42, 53, 58, 64, 68, 71],
61: [51, 55, 57, 65, 67],
62: [48, 50, 56, 63, 66],
63: [50, 59, 62, 66, 69, 70],
64: [52, 53, 60, 71],
65: [56, 57, 61, 66, 67, 72],
66: [56, 62, 63, 65, 70, 74, 75],
67: [61, 65, 72],
68: [58, 60, 69, 71, 73, 76],
69: [58, 59, 63, 68, 70, 73, 77],
70: [63, 66, 69, 74, 77],
71: [60, 64, 68, 76],
72: [65, 67, 75],
73: [68, 69, 76, 77],
74: [66, 70, 75, 77],
75: [66, 72, 74],
76: [68, 71, 73],
77: [69, 70, 73, 74]
}