关于MediaPipe从网络摄像头获取姿态地标坐标时出现‘NoneType object is not subscriptable’错误的技术问询
搞定这个NoneType错误的思路
嘿,我来帮你理清这个问题的根源!你遇到的'NoneType object is not subscriptable'错误,核心原因其实和网络摄像头的实时帧特性有关:
- 静态图片是固定的,MediaPipe Pose能稳定识别出画面里的人体姿态,所以
results.pose_landmarks永远是有值的,你直接访问landmark[0].x自然没问题。 - 但网络摄像头是实时输出帧的,偶尔会出现检测失败的情况:比如摄像头刚启动的初始化帧画面模糊、画面里暂时没有人体、或者光线差导致识别失效,这时候
results.pose_landmarks就会变成None。你这时候直接去用[0]下标访问,就相当于对None做下标操作,自然就报错了。
至于你说print(results.pose_landmarks)看起来都正常,大概率是你测试时刚好大部分帧都能成功识别,但程序运行时总有那么几帧会“掉链子”,刚好触发了错误。
修复代码的关键步骤
只需要在访问姿态地标之前,先加个判断,确认results.pose_landmarks不是None再执行后续操作。我帮你修改了代码,还加了一些小优化:
import mediapipe as mp import cv2 mpDraw = mp.solutions.drawing_utils mpPose = mp.solutions.pose pose = mpPose.Pose() # 切换为网络摄像头数据源 cap = cv2.VideoCapture(0) while True: ret, img = cap.read() # 先检查是否成功读取到摄像头帧(比如摄像头没连接的情况) if not ret: print("无法获取摄像头画面,请检查设备连接") break imgRGB = cv2.cvtColor(img, cv2.COLOR_BGR2RGB) results = pose.process(imgRGB) # 关键判断:只有检测到姿态时才访问地标 if results.pose_landmarks: # 现在可以安全地访问第一个地标的x坐标了 print(results.pose_landmarks.landmark[0].x) mpDraw.draw_landmarks(img, results.pose_landmarks, mpPose.POSE_CONNECTIONS) cv2.imshow("image", img) # 按q退出 if cv2.waitKey(1) == ord("q"): cap.release() cv2.destroyAllWindows() break
额外的小优化说明
- 加了
if not ret:的判断:防止摄像头无法正常输出帧的情况(比如权限没开、设备没连接)。 - 把
cap.release(0)改成了cap.release():release()方法不需要传参数,原来的写法是多余的。
这样修改后,程序会自动跳过那些识别失败的帧,再也不会触发NoneType错误,同时正常识别的帧能顺利打印坐标~
内容的提问来源于stack exchange,提问作者Teodor Apostol




