A*算法求解8数码问题报TypeError: cannot unpack non-iterable int如何修复
错误根因分析
报错的直接触发原因是Problem.successor方法存在多处语法和逻辑错误:
- 提前返回中断逻辑:定义完
candidate内部函数后多写了一行return state,直接导致successor方法提前返回状态列表,没有执行后续生成后继状态列表的逻辑。遍历状态列表时迭代到单个int元素,无法解包为(动作, 状态)二元组,直接抛出你遇到的类型错误。 candidate函数无返回值:该函数完成状态交换后没有返回修改后的新状态,即使修复提前返回问题,添加到后继列表的也只会是None。- 可解性判断逻辑错误:
getInvCount函数中设置的空块值为-1,但你的代码中空块用0表示,导致逆序数计算错误,可解性判断不准。 - (可选优化)后继位置边界判断可以直接校验坐标是否在0~2范围内,无需遍历字典查找,性能更高。
修复代码
1. 修复逆序数计算函数
def getInvCount(arr): inv_count = 0 empty_value = 0 # 空块值改为0,和状态定义对齐 for i in range(0, 9): for j in range(i + 1, 9): if arr[j] != empty_value and arr[i] != empty_value and arr[i] > arr[j]: inv_count += 1 return inv_count
2. 修复Problem类的successor方法
class Problem: def __init__(self, initial, goal=None): self.initial = initial; self.goal = goal def successor(self, state): reachable = [] index_state = coordinate(state) zero_position = index_state[0] move_pair = {"left":[zero_position[0], zero_position[1] - 1], "right":[zero_position[0], zero_position[1] + 1], "up":[zero_position[0] - 1, zero_position[1]], "down":[zero_position[0] + 1, zero_position[1]] } def get_key(val): for key, value in index_state.items(): if val == value: return key return -1 def candidate(state, Position): state = state.copy() zero_index = state.index(0) swap_index = state.index(get_key(Position)) state[zero_index], state[swap_index] = state[swap_index], state[zero_index] return state # 新增返回修改后的状态 for action, position in move_pair.items(): # 先校验坐标合法再生成状态 if 0 <= position[0] < 3 and 0 <= position[1] <3: new_state = candidate(state, position) reachable.append((action, new_state)) return reachable # 剩余goal_test、path_cost等方法保持不变
额外优化建议
你当前的路径去重逻辑是每次遍历整条父节点链判断状态是否重复,性能较低,可以改为直接用全局closed表判断即可,不需要每次遍历路径,能大幅提升搜索速度。
内容的提问来源于stack exchange,提问作者Jennie C.
相关产品推荐
相关产品推荐

