Python字典定义图的路径查找函数部分节点路径返回None问题排查
为什么我的路径查找函数在某些节点间返回None?
首先来看你定义的邻接矩阵和路径查找函数:
你的邻接矩阵定义
adj_matrix = { '1': set('2'), '2': set('3'), '3': set(['4', '5']), '4': set(''), '5': set('6'), '6': set('7'), '7': set('8'), '8': set(['9', '14']), '9': set(['10', '11']), '10': set(''), '11': set(['12', '13']), '12': set(''), '13': set(''), '14': set('15'), # 这里存在错误! '15': set('16'), # 这里存在错误! '16': set('17'), # 这里存在错误! '17': set(['18', '19']), '18': set(''), '19': set('') }
你的路径查找函数
def find_path(graph, start, end, path=[]): path = path + [start] if start == end: return path if start not in graph: return None for node in graph[start]: if node not in path: newpath = find_path(graph, node, end, path) if newpath: return newpath return None
问题根源:邻接矩阵的集合定义错误
你遇到的核心问题是两位数节点的集合创建方式有误。在Python中,set('15')这种写法会把字符串'15'拆分成单个字符,最终生成的集合是{'1', '5'},而不是你预期的{'15'}!
具体看你的邻接矩阵:
'14': set('15')实际生成的是{'1','5'},根本没有指向节点'15''15': set('16')生成{'1','6'},没有指向节点'16''16': set('17')生成{'1','7'},没有指向节点'17'
这就导致当函数走到节点'14'时,只会去遍历'1'和'5',完全找不到'15'节点,自然返回None。而'14'能被正常找到,是因为'8'的集合定义是正确的:set(['9', '14'])传入的是列表,集合里保留了完整的节点字符串'9'和'14'。
修复方法
把所有两位数节点的集合定义改成传入列表或者直接用集合字面量,确保节点字符串被完整识别:
修正后的邻接矩阵:
adj_matrix = { '1': {'2'}, '2': {'3'}, '3': {'4', '5'}, '4': set(), # 空集合更清晰的写法是set()或者{} '5': {'6'}, '6': {'7'}, '7': {'8'}, '8': {'9', '14'}, '9': {'10', '11'}, '10': set(), '11': {'12', '13'}, '12': set(), '13': set(), '14': {'15'}, # 修正:用集合字面量保留完整节点 '15': {'16'}, # 修正 '16': {'17'}, # 修正 '17': {'18', '19'}, '18': set(), '19': set() }
另外给你一个函数的小优化建议:Python中可变默认参数(比如path=[])可能会导致意外行为(因为默认参数只会初始化一次),可以改成如下写法:
def find_path(graph, start, end, path=None): # 初始化路径,避免可变默认参数的陷阱 path = path + [start] if path is not None else [start] if start == end: return path if start not in graph: return None for node in graph[start]: if node not in path: newpath = find_path(graph, node, end, path) if newpath: return newpath return None
验证修复结果
现在调用find_path(adj_matrix, '3', '15')会正常返回预期路径:
['3', '5', '6', '7', '8', '14', '15']
内容的提问来源于stack exchange,提问作者RezAm
相关产品推荐
相关产品推荐

