博主介绍:✌全网粉丝10W+,前互联网大厂软件研发、集结硕博英豪成立工作室。专注于计算机相关专业项目实战6年之久,选择我们就是选择放心、选择安心毕业✌
> 🍅想要获取完整文章或者源码,或者代做,拉到文章底部即可与我联系了。🍅点击查看作者主页,了解更多项目!
🍅感兴趣的可以先收藏起来,点赞、关注不迷路,大家在毕设选题,项目以及论文编写等相关问题都可以给我留言咨询,希望帮助同学们顺利毕业 。🍅
1、毕业设计:2026年计算机专业毕业设计选题汇总(建议收藏)✅
2、大数据毕业设计:2026年选题大全 深度学习 python语言 JAVA语言 hadoop和spark(建议收藏)✅
🍅感兴趣的可以先收藏起来,点赞、关注不迷路,大家在毕设选题,项目以及论文编写等相关问题都可以给我留言咨询,希望帮助同学们顺利毕业 。🍅
1、项目介绍
技术栈:
python语言、YOLO、Pyqt5界面、数据集
基于YOLO11/v10/v8/v5深度学习的危险驾驶行为检测识别系统设计与实现【python源码+Pyqt5界面+数据集+训练代码】
2、项目界面
(1)功能界面
(2)多目标检测识别
(3)多目标检测识别
(4)抽烟检测识别
(5)打电话检测识别
3、项目说明
摘要:随着道路交通安全意识的日益增强,如何有效预防交通事故成为了社会关注的重点之一,危险驾驶行为检测识别的重要性在于它能够主动识别并警示驾驶员的不当行为,从而减少由这些行为引发的交通事故。本文基于YOLOv11/v10/v8/v5的深度学习框架,通过6157张危险驾驶行为的相关图片,训练了可进行危险驾驶行为目标检测的模型,可以分别检测4种类别:[‘喝饮料’,‘吃东西’,‘用手机’,‘抽烟’],同时全面对比分析了YOLOv5n、YOLOv8n、YOLOv10n、YOLO11这4种模型在验证集上的评估性能表现。最终基于训练好的模型制作了一款带UI界面的危险驾驶行为检测识别系统,更便于进行功能的展示。该系统是基于python与PyQT5开发的,支持图片、视频以及摄像头进行目标检测,并保存检测结果。
主要工作内容
本文的主要内容包括以下几个方面:
搜集与整理数据集:搜集整理实际场景中危险驾驶行为的相关数据图片,并进行相应的数据处理,为模型训练提供训练数据集;
训练模型:基于整理的数据集,根据最前沿的YOLOv11/v10/v8/v5目标检测技术训练目标检测模型,实现对需要检测的对象进行有效检测的功能;
模型性能对比:对训练出的4种模型在验证集上进行了充分的结果评估和对比分析,主要目的是为了揭示每个模型在关键指标(如Precision、Recall、mAP50和mAP50-95等指标)上的优劣势。这不仅帮助我们在实际应用中选择最适合特定需求的模型,还能够指导后续模型优化和调优工作,以期获得更高的检测准确率和速度。最终,通过这种系统化的对比和分析,我们能更好地理解模型的鲁棒性、泛化能力以及在不同类别上的检测表现,为开发更高效的计算机视觉系统提供坚实的基础。
可视化系统制作:基于训练出的目标检测模型,搭配Pyqt5制作的UI界面,用python开发了一款界面简洁的软件系统,可支持图片、视频以及摄像头检测,同时可以将图片或者视频检测结果进行保存。其目的是为检测系统提供一个用户友好的操作平台,使用户能够便捷、高效地进行检测任务。
主要功能说明
功能视频演示见文章开头,以下是简要的操作描述。
(1)图片检测说明
点击打开图片按钮,选择需要检测的图片,或者点击打开文件夹按钮,选择需要批量检测图片所在的文件夹,操作演示如下:
点击目标下拉框后,可以选定指定目标的结果信息进行显示。
点击保存按钮,会对检测结果进行保存,存储路径为:save_data目录下,同时会将图片检测信息保存csv文件。
注:1.右侧目标位置默认显示置信度最大一个目标位置,可用下拉框进行目标切换。所有检测结果均在左下方表格中显示。
(2)视频检测说明
点击视频按钮,打开选择需要检测的视频,就会自动显示检测结果,再次点击可以关闭视频。
点击保存按钮,会对视频检测结果进行保存,存储路径为:save_data目录下。
(3)摄像头检测说明
点击打开摄像头按钮,可以打开摄像头,可以实时进行检测,再次点击,可关闭摄像头。
(4)保存图片与视频检测说明
点击保存按钮后,会将当前选择的图片【含批量图片】或者视频的检测结果进行保存,对于图片图片检测还会保存检测结果为csv文件,方便进行查看与后续使用。检测的图片与视频结果会存储在save_data目录下。
4、核心代码
# encoding:utf-8importcv2fromPyQt5.QtGuiimportQPixmap,QImageimportnumpyasnpfromPILimportImage,ImageDraw,ImageFontimportcsvimportos# fontC = ImageFont.truetype("Font/platech.ttf", 20, 0)# 绘图展示defcv_show(name,img):cv2.imshow(name,img)cv2.waitKey(0)cv2.destroyAllWindows()defdrawRectBox(image,rect,addText,fontC,color):""" 绘制矩形框与结果 :param image: 原始图像 :param rect: 矩形框坐标, int类型 :param addText: 类别名称 :param fontC: 字体 :return: """# 绘制位置方框cv2.rectangle(image,(rect[0],rect[1]),(rect[2],rect[3]),color,2)# 绘制字体背景框cv2.rectangle(image,(rect[0]-1,rect[1]-25),(rect[0]+60,rect[1]),color,-1,cv2.LINE_AA)# 图片 添加的文字 位置 字体 字体大小 字体颜色 字体粗细# cv2.putText(image, addText, (int(rect[0])+2, int(rect[1])-3), cv2.FONT_HERSHEY_SIMPLEX, 0.8, (255, 255, 255), 2)img=Image.fromarray(image)draw=ImageDraw.Draw(img)draw.text((rect[0]+2,rect[1]-27),addText,(255,255,255),font=fontC)imagex=np.array(img)returnimagexdefimg_cvread(path):# 读取含中文名的图片文件# img = cv2.imread(path)img=cv2.imdecode(np.fromfile(path,dtype=np.uint8),cv2.IMREAD_COLOR)returnimgdefdraw_boxes(img,boxes):foreachinboxes:x1=each[0]y1=each[1]x2=each[2]y2=each[3]cv2.rectangle(img,(x1,y1),(x2,y2),(0,255,0),2)returnimgdefcvimg_to_qpiximg(cvimg):height,width,depth=cvimg.shape cvimg=cv2.cvtColor(cvimg,cv2.COLOR_BGR2RGB)qimg=QImage(cvimg.data,width,height,width*depth,QImage.Format_RGB888)qpix_img=QPixmap(qimg)returnqpix_imgdefsave_video():# VideoCapture方法是cv2库提供的读取视频方法cap=cv2.VideoCapture('C:\\Users\\xxx\\Desktop\\sweet.mp4')# 设置需要保存视频的格式“xvid”# 该参数是MPEG-4编码类型,文件名后缀为.avifourcc=cv2.VideoWriter_fourcc(*'XVID')# 设置视频帧频fps=cap.get(cv2.CAP_PROP_FPS)# 设置视频大小size=(int(cap.get(cv2.CAP_PROP_FRAME_WIDTH)),int(cap.get(cv2.CAP_PROP_FRAME_HEIGHT)))# VideoWriter方法是cv2库提供的保存视频方法# 按照设置的格式来out输出out=cv2.VideoWriter('C:\\Users\\xxx\\Desktop\\out.avi',fourcc,fps,size)# 确定视频打开并循环读取while(cap.isOpened()):# 逐帧读取,ret返回布尔值# 参数ret为True 或者False,代表有没有读取到图片# frame表示截取到一帧的图片ret,frame=cap.read()ifret==True:# 垂直翻转矩阵frame=cv2.flip(frame,0)out.write(frame)cv2.imshow('frame',frame)ifcv2.waitKey(1)&0xFF==ord('q'):breakelse:break# 释放资源cap.release()out.release()# 关闭窗口cv2.destroyAllWindows()# 封装函数:图片上显示中文defcv2AddChineseText(img,text,position,textColor=(0,255,0),textSize=50):if(isinstance(img,np.ndarray)):# 判断是否OpenCV图片类型img=Image.fromarray(cv2.cvtColor(img,cv2.COLOR_BGR2RGB))# 创建一个可以在给定图像上绘图的对象draw=ImageDraw.Draw(img)# 字体的格式fontStyle=ImageFont.truetype("simsun.ttc",textSize,encoding="utf-8")# 绘制文本draw.text(position,text,textColor,font=fontStyle)# 转换回OpenCV格式returncv2.cvtColor(np.asarray(img),cv2.COLOR_RGB2BGR)definsert_rows(path,lines,header):""" 将n行数据写入csv文件 :param path: :param lines: :return: """no_header=Falseifnotos.path.exists(path):no_header=Truestart_num=1else:start_num=len(open(path).readlines())csv_head=headerwithopen(path,'a',newline='')asf:csv_write=csv.writer(f)ifno_header:csv_write.writerow(csv_head)# 写入表头foreach_listinlines:# 添加序号each_list=[start_num]+each_list csv_write.writerow(each_list)# 序号 + 1start_num+=1classColors:# 用于绘制不同颜色def__init__(self):"""Initialize colors as hex = matplotlib.colors.TABLEAU_COLORS.values()."""hexs=('FF3838','FF9D97','FF701F','FFB21D','CFD231','48F90A','92CC17','3DDB86','1A9334','00D4BB','2C99A8','00C2FF','344593','6473FF','0018EC','8438FF','520085','CB38FF','FF95C8','FF37C7')self.palette=[self.hex2rgb(f'#{c}')forcinhexs]self.n=len(self.palette)self.pose_palette=np.array([[255,128,0],[255,153,51],[255,178,102],[230,230,0],[255,153,255],[153,204,255],[255,102,255],[255,51,255],[102,178,255],[51,153,255],[255,153,153],[255,102,102],[255,51,51],[153,255,153],[102,255,102],[51,255,51],[0,255,0],[0,0,255],[255,0,0],[255,255,255]],dtype=np.uint8)def__call__(self,i,bgr=False):"""Converts hex color codes to rgb values."""c=self.palette[int(i)%self.n]return(c[2],c[1],c[0])ifbgrelsec@staticmethoddefhex2rgb(h):# rgb order (PIL)returntuple(int(h[1+i:1+i+2],16)foriin(0,2,4))defyolo_to_location(w,h,yolo_data):# yolo文件转两点坐标,注意画图坐标要转换成int格式x_,y_,w_,h_=yolo_data x1=int(w*x_-0.5*w*w_)x2=int(w*x_+0.5*w*w_)y1=int(h*y_-0.5*h*h_)y2=int(h*y_+0.5*h*h_)# cv2.rectangle(img, (int(x1), int(y1)), (int(x2), int(y2)), (255, 0, 0))return[x1,y1,x2,y2]deflocation_to_yolo(w,h,locations):# x1,y1左上角坐标,x2,y2右上角坐标x1,y1,x2,y2=locations x_=(x1+x2)/2/w x_=float('%.5f'%x_)y_=(y1+y2)/2/h y_=float('%.5f'%y_)w_=(x2-x1)/w w_=float('%.5f'%w_)h_=(y2-y1)/h h_=float('%.5f'%h_)return[x_,y_,w_,h_]defdraw_yolo_data(img_path,yolo_file_path):# 读取yolo标注数据并显示img=cv2.imread(img_path)h,w,_=img.shapeprint(img.shape)# yolo标注数据文件名为786_rgb_0616.txtwithopen(yolo_file_path,'r')asf:data=f.readlines()foreachindata:temp=each.split()# ['1', '0.43906', '0.52083', '0.34687', '0.15']# YOLO转换为两点坐标x1, x2, y1, y2x_,y_,w_,h_=eval(temp[1]),eval(temp[2]),eval(temp[3]),eval(temp[4])x1,y1,x2,y2=yolo_to_location(w,h,[x_,y_,w_,h_])# 画图验证框是否正确cv2.rectangle(img,(x1,y1),(x2,y2),(0,0,255))cv2.imshow('windows',img)cv2.waitKey(0)if__name__=='__main__':img_path='TestFiles/1.jpg'yolo_file_path='save_data/yolo_labels/1.txt'draw_yolo_data(img_path,yolo_file_path)5、源码获取方式
🍅由于篇幅限制,获取完整文章或源码、代做项目的,查看【用户名】、【专栏名称】就可以找到我啦🍅
感兴趣的可以先收藏起来,点赞、关注不迷路,下方查看👇🏻获取联系方式👇🏻