如何将树莓派上深度学习模型的预测结果发送至网页端进行处理
树莓派深度学习预测结果同步到网页端实现方案
采用WebSocket实时推送方案,适配实时摄像头预测场景,延迟低、性能开销小,适合树莓派运行。
步骤1:安装依赖
在树莓派终端执行命令:pip install flask flask-sock
步骤2:改造现有模型代码
替换原有代码为以下版本,保留原有预测逻辑,新增Web服务和结果推送能力:
import cv2 import tensorflow.keras as keras import numpy as np import time import threading from flask import Flask, render_template from flask_sock import Sock # 初始化Web服务 app = Flask(__name__) sock = Sock(app) latest_prediction = [] # 首页路由 @app.route('/') def index(): return render_template('index.html') # WebSocket推送路由 @sock.route('/ws') def ws_conn(ws): while True: if latest_prediction: send_content = '\n'.join([f'{item[0]}: {item[1]}' for item in latest_prediction]) ws.send(send_content) time.sleep(0.1) # 原有模型逻辑 np.set_printoptions(suppress=True) webcam = cv2.VideoCapture(0) model = keras.models.load_model('keras_model.h5') data_for_model = np.ndarray(shape=(1, 224, 224, 3), dtype=np.float32) def load_labels(path): f = open(path, 'r') lines = f.readlines() labels = [] for line in lines: labels.append(line.split(' ')[1].strip('\n')) return labels label_path = 'labels.txt' labels = load_labels(label_path) print(labels) def image_resize(image, height, inter=cv2.INTER_AREA): dim = None (h, w) = image.shape[:2] r = height / float(h) dim = (int(w * r), height) resized = cv2.resize(image, dim, interpolation=inter) return resized def cropTo(img): size = 224 height, width = img.shape[:2] sideCrop = (width - 224) // 2 return img[:, sideCrop:(width - sideCrop)] # 模型运行逻辑单独放子线程 def run_model(): global latest_prediction while True: ret, img = webcam.read() if ret: img = image_resize(img, height=224) img = cropTo(img) img = cv2.flip(img, 1) normalized_img = (img.astype(np.float32) / 127.0) - 1 data_for_model[0] = normalized_img prediction = model.predict(data_for_model, verbose=0) # 更新最新预测结果 pred_list = [] for i in range(0, len(prediction[0])): pred_list.append((labels[i], prediction[0][i])) latest_prediction = pred_list cv2.imshow('webcam', img) if cv2.waitKey(1) == 27: break cv2.destroyAllWindows() if __name__ == '__main__': # 启动模型子线程 threading.Thread(target=run_model, daemon=True).start() # 启动Web服务,允许局域网访问 app.run(host='0.0.0.0', port=5000, debug=False)
步骤3:新增前端页面
在Python代码同目录下新建templates文件夹,在文件夹内新建index.html文件,内容如下:
<!DOCTYPE html> <html lang="zh-CN"> <head> <meta charset="UTF-8"> <title>模型预测结果</title> </head> <body> <h2>实时预测结果</h2> <pre id="pred_result"></pre> <script> // 建立WebSocket连接 const ws = new WebSocket(`ws://${location.host}/ws`); ws.onmessage = (e) => { // 渲染预测结果 document.getElementById('pred_result').textContent = e.data; // 后续可在此处新增绘图、提交数据到后端存库等逻辑 } </script> </body> </html>
运行验证
- 树莓派上运行修改后的Python脚本
- 确认访问设备和树莓派在同一局域网,查询树莓派的局域网IP
- 浏览器访问
http://树莓派IP:5000即可查看实时预测结果
拓展功能实现说明
- 数据存入数据库:直接在后端
run_model函数的预测逻辑后新增数据库插入代码即可,支持SQLite、MySQL等常见数据库 - 结果可视化:前端可引入图表库,将拿到的预测结果渲染为折线图、柱状图等
- 外网访问:需要公网访问时,配置内网穿透工具映射树莓派5000端口即可
内容的提问来源于stack exchange,提问作者james
相关产品推荐
相关产品推荐

