Flask+Python+MySQL环境下YOLOv5检测程序报错及自动关闭问题
问题修复方案
1. 解决AttributeError: 'tuple' object has no attribute 'encode'错误
问题根源
get_product_data函数查询到数据时返回元组(message, image_data),但detect_objects中直接对返回值调用encode()方法,元组没有该方法;同时函数返回值类型不统一,无数据时会引发未定义变量的错误。
修复代码
修改get_product_data函数
def get_product_data(object_name): cnx = mysql.connector.connect(user='root', password='', host='localhost', database='product') cursor = cnx.cursor() # 改用参数化查询避免SQL注入 query = "SELECT * FROM information WHERE product_name = %s" cursor.execute(query, (object_name,)) data = cursor.fetchone() select_query = "SELECT image_data FROM information WHERE product_name = %s" cursor.execute(select_query, (object_name,)) result = cursor.fetchone() cursor.close() cnx.close() if data: message = f"<br>產品名稱:{data[1]}<br>價格:{data[2]}<br>折扣價格:{data[3]}<br>折扣:{data[4]}<br>" image_data = result[0] if result else None return message, image_data else: return None, None
修改detect_objects中的调用逻辑
# 替换原有的分判断逻辑,统一处理 if object_name not in object_names: object_names.append(object_name) message, _ = get_product_data(object_name) if message: yield message.encode()
2. 解决程序偶尔自动关闭的问题
问题根源
stop_video中调用cap.release()释放摄像头后,后续无法重新打开导致程序崩溃- 摄像头初始化无异常处理,启动失败直接报错
- 循环中的
break导致只处理第一个检测物体,引发逻辑异常
修复代码
修改stop_video和resume_video接口
@app.route('/stop_video', methods=['POST']) def stop_video(): global video_paused video_paused = True # 不直接释放摄像头,保留重启能力 return '已停止' @app.route('/resume_video', methods=['POST']) def resume_video(): global video_paused, cap, height, width, baseline video_paused = False # 摄像头已释放则重新初始化 if not cap.isOpened(): cap = cv2.VideoCapture(0) success, frame = cap.read() if success: height, width, _ = frame.shape baseline = height // 2 + 100 return '已繼續'
移除detect_objects中的多余break
for obj in detected_objects: obj_class = int(obj[-1]) if obj_class in [0, 1, 2]: obj_center_x = (obj[0] + obj[2]) / 2 + 100 obj_center_y = (obj[1] + obj[3]) / 2 + 100 if obj_center_y > baseline: object_name = "" if obj_class == 0: object_name = "柚香" elif obj_class == 1: object_name = "福樂" elif obj_class == 2: object_name = "美祿" if object_name not in object_names: object_names.append(object_name) message, _ = get_product_data(object_name) if message: yield message.encode() # 移除此处的break,确保遍历所有检测物体
3. 其他优化点
- 简化
product_page逻辑,避免重复判断:
@app.route('/product_page') def product_page(): object_name = request.args.get('object_name') message = None image_base64 = None if object_name: message, image_data = get_product_data(object_name) if image_data: image_base64 = base64.b64encode(image_data).decode('utf-8') return render_template('product_page.html', message=message, image_data=image_base64)
内容的提问来源于stack exchange,提问作者TanNeil
相关产品推荐
相关产品推荐

