Python YOLO项目if分支定义的pallet_center_x跨分支引用报NameError如何解决
问题原因与解决方法
根本原因
global pallet_center_x仅声明该变量使用全局作用域,不会自动创建变量。只有当c==1的分支实际执行过一次,pallet_center_x才会被赋值生成。- 你当前这段代码运行在YOLO逐检测框遍历的逻辑中,检测目标的顺序是不固定的,完全可能先检测到类别为2的孔,此时
c==1的分支从未执行,pallet_center_x不存在,就会触发NameError。
修复方案
方案1:提前初始化全局变量(最简单通用)
在所有if分支、甚至函数外层的全局作用域,提前给变量赋初始值,同时在引用前加校验避免逻辑错误:
# 全局作用域提前初始化(放在你的detect函数外面即可) pallet_center_x = None pallet_center_y = None
然后修改c==2分支的逻辑,先校验变量是否已被赋值:
if c == 2: # pallet hole # 未检测到托盘时直接跳过孔的处理 if pallet_center_x is None: pass else: hole_x00 = int(x_top) # + int(width / 2) hole_y00 = int(y_top) # + int(height/2) hole_x01 = int(x_top + width) hole_y10 = int(y_top + height) hole_centre_x = int((hole_x01 + hole_x00) / 2) hole_centre_y = int((hole_y00 + hole_y10) / 2) if hole_centre_x < pallet_center_x: plot_one_box(xyxy, im0, label=label, color=colors(c, True), line_thickness=2) cv2.circle(im0, (hole_centre_x, hole_centre_y), 2, (0, 255, 0), -1) # center-point
方案2:封装为类属性(更规范,适合工程代码)
如果你的检测逻辑是用类实现的,可以把托盘中心坐标定义为类的实例属性,初始化时就完成赋值,避免全局变量滥用:
class YoloDetector: def __init__(self): self.pallet_center_x = None self.pallet_center_y = None def detect(self): # 原有检测逻辑 for *xyxy, conf, cls in det: c = int(cls) if c ==1: # 原有计算逻辑 self.pallet_center_x = int((pallet_x01 + pallet_x00) / 2) if c ==2: if self.pallet_center_x is None: continue # 原有孔处理逻辑
内容的提问来源于stack exchange,提问作者inharang2220
相关产品推荐
相关产品推荐

