YOLO系列解读DAY1—YOLOV1预训练模型

为什么需要预训练模型 替换模型A的最后几层(与分类相关的层),并针对新的猫狗分类数据进行训练。 阅读详情

一、说在前面

小伙伴们好,博主很久没有写博客了,略感生疏,不到之处敬请谅解,欢迎指出文中错误,大家一起探讨。欲看视频讲解,可转至博主DouYin、B站,欢迎关注,链接如下:

Github:GitHub - samylee/ExtractionNet: yolov1 extractionnet to pytorch

DY:samylee_csdn

B站:samylee

二、博客系列链接

YOLO系列解读DAY1—YOLOV1预训练模型

YOLO系列解读DAY2—YOLOV1预测代码转换

三、YOLOV1预训练模型

众所周知,在当时预训练模型的性能会直接影响整个检测网络的效果,所以设计出一款好的分类模型是做检测任务的必经之路。分类网络原理部分这里不做进一步阐述了,博主会开设另外系列博客讲解分类网络,敬请期待。

Darknet作者采用自研的extraction网络,在当时已经达到SOTA水平,且速度明显优于同时期SOTA模型,性能如下图所示。

​

网络设计方面作者采用直到型架构,因当时何恺明等大神尚未提出残差网络,所以直到型还是主流网络架构,如下图所示,其中'M'表示最大池化层,'A'表示平均池化层。

​

四、Extraction网络转PyTorch

网络转换需要注意三个地方:

1、要求将Extraction网络按照其特定的网络序列复写出PyTorch的网络架构,切不可心浮气躁;

2、Darknet存储参数的序列和PyTorch稍有不同,若遇到BatchNorm架构的卷积层,Darknet会先存储BatchNorm层的参数,进而存储卷积层的参数;

3、图像数据预处理部分,Darknet分类网络的顺序是:BGR2RGB->Norm(1/255)->Resize->Crop,所以我们在复现的时候一定要按照该顺序进行数据预处理操作。

网络复现如下,版本PyTorch1.4,Python3.6,博主暂未加PyTorch的训练代码,因ImageNet训练时间较长,所以直接使用了Extraction的网络模型,若有需要的小伙伴可以评论或私信给博主,博主可添加Extraction分类网络的PyTorch的训练方法。

import torch
import torch.nn as nn
import torch.nn.functional as F
import cv2
import numpy as np


class ExtractionNet(nn.Module):
    def __init__(self, in_channels=3, num_classes=1000, init_weights=True, phase='train'):
        super(ExtractionNet, self).__init__()
        self._phase = phase
        self.features = self.make_layers(in_channels=in_channels, out_channels=num_classes)
        if init_weights:
            self._initialize_weights()

    def forward(self, x):
        for feature in self.features:
            x = feature(x)

        if self._phase == 'test':
            x = torch.flatten(x, 1)
            x = F.softmax(x, dim=-1)
        return x

    def _initialize_weights(self):
        for m in self.modules():
            if isinstance(m, nn.Conv2d):
                nn.init.kaiming_normal_(m.weight, mode='fan_in', nonlinearity='leaky_relu')
                if m.bias is not None:
                    nn.init.constant_(m.bias, 0)
            elif isinstance(m, nn.BatchNorm2d):
                nn.init.constant_(m.weight, 1)
                nn.init.constant_(m.bias, 0)
            elif isinstance(m, nn.Linear):
                nn.init.normal_(m.weight, 0, 0.01)
                nn.init.constant_(m.bias, 0)

    def make_layers(self, in_channels=3, out_channels=1000):
        # conv: out_channels, kernel_size, stride, batchnorm, activate
        # maxpool: kernel_size stride
        params = [
            [64, 7, 2, True, 'leaky'],
            ['M', 2, 2],
            [192, 3, 1, True, 'leaky'],
            ['M', 2, 2],
            [128, 1, 1, True, 'leaky'],
            [256, 3, 1, True, 'leaky'],
            [256, 1, 1, True, 'leaky'],
            [512, 3, 1, True, 'leaky'],
            ['M', 2, 2],
            [256, 1, 1, True, 'leaky'],
            [512, 3, 1, True, 'leaky'],
            [256, 1, 1, True, 'leaky'],
            [512, 3, 1, True, 'leaky'],
            [256, 1, 1, True, 'leaky'],
            [512, 3, 1, True, 'leaky'],
            [256, 1, 1, True, 'leaky'],
            [512, 3, 1, True, 'leaky'],
            [512, 1, 1, True, 'leaky'],
            [1024, 3, 1, True, 'leaky'],
            ['M', 2, 2],
            [512, 1, 1, True, 'leaky'],
            [1024, 3, 1, True, 'leaky'],
            [512, 1, 1, True, 'leaky'],
            [1024, 3, 1, True, 'leaky'],
            [out_channels, 1, 1, False, 'leaky'], # classifier
            ['A']
        ]

        module_list = nn.ModuleList()
        for i, v in enumerate(params):
            modules = nn.Sequential()
            if v[0] == 'M':
                modules.add_module(f"maxpool_{i}", nn.MaxPool2d(kernel_size=v[1], stride=v[2], padding=int((v[1] - 1) // 2)))
            elif v[0] == 'A':
                modules.add_module(f"avgpool_{i}", nn.AdaptiveAvgPool2d((1, 1)))
            else:
                modules.add_module(
                    f"conv_{i}",
                    nn.Conv2d(
                        in_channels,
                        v[0],
                        kernel_size=v[1],
                        stride=v[2],
                        padding=(v[1] - 1) // 2,
                        bias=not v[3]
                    )
                )
                if v[3]:
                    modules.add_module(f"bn_{i}", nn.BatchNorm2d(v[0]))
                modules.add_module(f"act_{i}", nn.LeakyReLU(0.1) if v[4] == 'leaky' else nn.ReLU())
                in_channels = v[0]
            module_list.append(modules)
        return module_list


def load_darknet_weights(model, weights_path):
    # Open the weights file
    with open(weights_path, "rb") as f:
        # First five are header values
        header = np.fromfile(f, dtype=np.int32, count=4)
        header_info = header  # Needed to write header when saving weights
        seen = header[3]  # number of images seen during training
        weights = np.fromfile(f, dtype=np.float32)  # The rest are weights

    ptr = 0
    for module in model.features:
        if isinstance(module[0], nn.Conv2d):
            conv_layer = module[0]
            if isinstance(module[1], nn.BatchNorm2d):
                # Load BN bias, weights, running mean and running variance
                bn_layer = module[1]
                num_b = bn_layer.bias.numel()  # Number of biases
                # Bias
                bn_b = torch.from_numpy(
                    weights[ptr: ptr + num_b]).view_as(bn_layer.bias)
                bn_layer.bias.data.copy_(bn_b)
                ptr += num_b
                # Weight
                bn_w = torch.from_numpy(
                    weights[ptr: ptr + num_b]).view_as(bn_layer.weight)
                bn_layer.weight.data.copy_(bn_w)
                ptr += num_b
                # Running Mean
                bn_rm = torch.from_numpy(
                    weights[ptr: ptr + num_b]).view_as(bn_layer.running_mean)
                bn_layer.running_mean.data.copy_(bn_rm)
                ptr += num_b
                # Running Var
                bn_rv = torch.from_numpy(
                    weights[ptr: ptr + num_b]).view_as(bn_layer.running_var)
                bn_layer.running_var.data.copy_(bn_rv)
                ptr += num_b
            else:
                # Load conv. bias
                num_b = conv_layer.bias.numel()
                conv_b = torch.from_numpy(weights[ptr: ptr + num_b]).view_as(conv_layer.bias)
                conv_layer.bias.data.copy_(conv_b)
                ptr += num_b
            # Load conv. weights
            num_w = conv_layer.weight.numel()
            conv_w = torch.from_numpy(weights[ptr: ptr + num_w]).view_as(conv_layer.weight)
            conv_layer.weight.data.copy_(conv_w)
            ptr += num_w


if __name__ == '__main__':
    # load moel
    checkpoint_path = "extraction.weights"
    model = ExtractionNet(phase='test')
    load_darknet_weights(model, checkpoint_path)
    model.eval()

    # model input size
    net_size = 224

    # load img
    img = cv2.imread('dog.jpg')
    # img bgr2rgb
    img_rgb = cv2.cvtColor(img, cv2.COLOR_BGR2RGB)

    # resize img
    h, w, _ = img_rgb.shape
    new_h, new_w = h, w
    if w < h:
        new_h = (h * net_size) // w
        new_w = net_size
    else:
        new_w = (w * net_size) // h
        new_h = net_size
    img_resize = cv2.resize(img_rgb, (new_w, new_h))

    # crop img
    cut_w = (new_w - net_size) // 2
    cut_h = (new_h - net_size) // 2
    img_crop = img_resize[cut_h:cut_h + net_size, cut_w:cut_w + net_size, :]

    # float
    img_crop = torch.from_numpy(img_crop.transpose((2, 0, 1)))
    img_float = img_crop.float().div(255).unsqueeze(0)

    # forward
    result = model(img_float)

    print(result.topk(5))

五、写在后面

小伙伴们若能坚持完成YOLO系列的代码和原理学习,相信能对图像检测任务有个全新的认识,跟随博主的脚步,培养自己的动手能力吧!希望博主也能坚持将该系列做下去,一起加油!!!

六、参考

1、ImageNet Classification

2、https://github.com/AlexeyAB/darknet

yolov8官方代码训练模型(coco数据集和voc数据集训练)+onnx模型预测 根据官方的解释,pip 的 ultralytics 库包含了 requirements.txt中的所有库。windows11 和 Ubuntu20.04(建议使用 Linux 系统)首先切换到自己建立的虚拟环境安装 pytorch。参照官网,直接使用以下语句即可导入项目所需要的库。train 和 val 的路径就这样写。2.3 yaml文件。 阅读详情

相关推荐

【YOLOv7训练】——预训练重使用

最后个人建议,能不用YOLOv7就别用!!!别用!!!别用!!! 训练真的太慢了!!!训练真的太慢了!!!训练真的太慢了!!!(OTA的锅,关了OTA会快好几倍,但性能会下降) 太吃显存了!!!太吃显存了!!!太吃显存了!!! 收敛曲线很魔鬼!!!收敛曲线很魔鬼!!!收敛曲线很魔鬼!!! 重要的事情说三遍!!!重要的事情说三遍!!!重要的事情说三遍!!!

retainenergy的博客 1万+

目标检测---教你利用yolov5训练自己的目标检测模型

目标检测---教你利用yolov5训练自己的目标检测模型

jiaoty19的博客 1万+

【YOLOv8实战】手把手带你入门YOLOv8,你也能训练自己的检测器,以SAR目标检测为例(源码+数据集+Gradio界面)

基于YOLOv8的SAR图像目标检测系统,覆盖数据制作、数据可视化、模型训练/评估/推理/部署全流程,最后通过 Gradio 界面进行展示。

u010522887的专栏 6754

YOLOv5模型训练

一、准备 要求:Python>=3.8以及PyTorch>=1.7 $ git clone https://github.com/ultralytics/yolov5 # clone repo $ cd yolov5 $ pip install -r requirements.txt # install 二、创建dataset.yaml 这里我们使用COCO128训练集,该训练集有128张图片用于训练和验证。 数据集配置文件定义如下: # 训练集和验证集目录 train: ../coc

康康的博客 2803

基于YOLO系列模型的牧场羊行为检测系统完整实现方案

目标检测作为计算机视觉的核心技术,通过深度学习算法实现对图像中特定目标的定位与识别。其原理基于卷积神经网络提取特征,结合边界框回归和分类器实现精准检测。在智慧农业领域,目标检测技术能够显著提升生产效率和管理水平,特别适用于动物行为监测等场景。YOLO系列模型以其高效的实时检测能力,在牧场智能化管理中展现出重要价值。结合PyQt图形界面和MySQL数据库,可以构建完整的羊只行为检测系统,实现对进食、饮水、休息等关键行为的自动识别与记录。该系统通过YOLOv5/v8等先进算法,解决了传统人工观察效率低下的问题,

570

【目标检测-YOLO】YOLO v5 训练最好结果的技巧

来自:Tips for Best Training Results 📌 - YOLOv5 Documentation Tips for Best Training Results 训练最好结果的技巧 👋 Hello! 📚 This guide explains how to produce the best mAP and training results with YOLOv5 🚀. Most of the time good results can be obtained with no cha

博观约取,厚积薄发 9963

YOLO系列解读DAY2—YOLOV1预测代码转换

需要注意yolov1全连接层的数据排序,其输出的channels=(S*S*(5*B+C))=1470,前7x7x20存储的是voc20类的概率,中间7x7x2存储的是2个矩形框的目标概率,最后7x7x2x4存储的是2个矩形框的边框信息。从上图可以看出yolov1-tiny的网络架构较为简单,只是采用卷积层和全连接层累加的形式,但并不能否认该网络在当时是开山之作,后面的架构都是基于该架构的思想进行创作的!小伙伴们好,博主很久没有写博客了,略感生疏,不到之处敬请谅解,欢迎指出文中错误,大家一起探讨。

samylee的博客 453

在Rust中使用Torch——Day 1:环境配置和使用PyTorch进行Yolov8推理

Rust是一种系统级编程语言,以其安全性、性能和并发性而闻名。而PyTorch是一个流行的机器学习框架,提供了丰富的工具和库来构建和训练深度学习模型。本文将介绍如何在Rust中配置环境,并使用PyTorch进行Yolov8目标检测模型的推理。

Bsv___的博客 750

姿态估计进阶:从 YOLO-NAS Pose 到 YOLOv8 Pose的技术探索与实践

摘要: YOLO-NAS Pose是Deci AI基于神经架构搜索(NAS)技术开发的新一代姿态估计模型,通过AutoNAC引擎优化架构,在精度与效率上超越YOLOv8 Pose。该模型提供四种尺寸变体,适配不同硬件需求,支持图像、视频等多源数据输入。实验显示其在直立人形检测中表现优异,但在水平姿态场景下略逊于YOLOv8。此外,文章还探讨了基于YOLOv8 Pose的瑜伽姿势分类实践,包括数据集准备与训练流程。YOLO-NAS Pose为实时姿态估计设定了新标杆,但在特定场景仍有优化空间。

知来者逆的博客 1231

从门禁到支付:Uniapp+NFC开发避坑指南(支持Mifare Classic)

本文详细介绍了Uniapp结合NFC技术开发门禁与支付系统的实战指南,特别针对Mifare Classic卡片进行深度优化。内容涵盖环境配置、设备兼容性处理、卡片安全机制解析以及高性能读写优化策略,帮助开发者快速实现跨平台的智能硬件交互解决方案。

t1u2v的博客 751

多相机标定与单应变换:用OpenCV实现BEV俯视全景图

多路监控画面分散在不同屏幕,难以快速理解全局空间关系。通过相机标定与畸变校正,利用单应矩阵将各视角图像投影到统一的地面坐标系,即可合成BEV鸟瞰全景图。该技术是车载360°环视系统和自动驾驶BEV感知的雏形,也适用于场地安防与移动机器人导航。基于Python+OpenCV的四路相机实现,完整覆盖标定、投影变换、多路羽化融合与实时优化,为多视角拼接和俯视全景图项目提供可复现的工程参考。

weixin_29056865的博客 244

【课程总结】Day12:YOLO的深入了解

在【课程总结】Day11(下):YOLO的入门使用一节中,我们已经了解YOLO的使用方法,使用过程非常简单,训练时只需要三行代码:引入YOLO,构建模型,训练模型;预测时也同样简单,只需要两行代码:引入YOLO,预测图像即可。

Deadwalk的专栏 1622

香橙派5B-RK3588-NPU内核升级至0.9.8:RKLLM多模态部署实战

本文详细介绍了香橙派5B-RK3588设备NPU内核升级至0.9.8版本的完整流程,重点讲解了升级的必要性、两种升级方案(预编译包安装与自行编译内核)以及RKLLM SDK的安装配置。通过实战演示多模态模型转换与推理,显著提升AI计算性能,为嵌入式AI部署提供实用指南。

salt9的博客 1026

Day 29:YOLO系列详解 — 从v1到v10

15天深度学习知识回顾 + 30道选择题 + 综合实战项目🔥。

2603_95724866的博客 377

k8s 查看cpu使用率最高的pod

在 Kubernetes 中,可以使用命令查看 Pod 的资源使用情况,从而找到 CPU 使用率最高的 Pod。

u010674101的专栏 3345

电商平台系统需求规格说明书(示例)

​​电商系统​​:指本文件所描述的集商品展示、销售、支付、物流跟踪、用户管理等功能于一体的综合性在线购物平台。​​API​​:应用程序编程接口(Application Programming Interface),用于实现系统各模块之间或与外部系统之间的数据交互和功能调用。

跟佟格湾一起学习计算机知识吧~ 1262

Day13 项目任务回顾

算法要达到的目的:电梯间电动车:识别电梯间内是否有电动车进入,若检测到电动车则在画面中报警,避免可能存在的安全隐患,实现电动车安全管控。(1)person:人(2)head:人头,人头框在person框内(3)door_open:电梯完全打开(4)door_half_open:电梯半开状态(5)door_close:电梯关闭状态(6)daizi:塑料袋、垃圾袋、编织袋、蛇皮袋、麻袋、购物袋(7)bottle:矿泉水瓶、易拉罐瓶、啤酒瓶等瓶子(8)bag:背包、手提包、斜挎包、单肩包。

m0_65638363的博客 881

数据本体论如何指导数仓建模?

数据本体论指导数仓建模的核心在于构建业务语义与数据结构的桥梁。该方法从业务域中抽象标准化知识体系,包含核心概念、属性、关系和规则五大要素,并将其映射为分层数仓模型。通过"业务本体梳理→本体建模→模型映射→治理迭代"的流程,实现数仓从"结构存储"到"语义载体"的升级。相比传统建模,该方法能解决语义不一致、跨域融合难等问题,使数仓具备更好的可扩展性和业务对齐性。实践表明,以数据本体论为指导的数仓建模能显著提升数据资产的可理解性和复用价值。

石榴姐yyds 395

YOLO-day2-yolo5

day2-yolo5。

keep_keeprogress的博客 285

写给开发人员的实用密码学 - Hash算法

说到Hash(哈希),开发人员应该不陌生,比如Hash表是一种非常常用的数据结构,通过Hash表能够根据键值快速找到数据。哈希函数将文本(或其他数据)映射为整数,从而能够提高检索效率。密...

云水木石 1503

python实现下载和离线安装包环境

导出当前电脑python安装的所有包列表requirement.txt。

m0_60352504的博客 1676

CV——day69:YOLO9000: Better, Faster, Stronger(已完结)

YOLO9000是一个通过联合优化检测和分类来检测9000多个对象类别的实时框架。我们使用WordTree联合收割机来自不同来源的数据,并使用联合优化技术在ImageNet和COCO上同时进行训练。YOLO9000是缩小检测和分类之间数据集大小差距的有力一步

想太多的学习日志 1105

C# WinForm 基于DirectShow.dll编写的程序,可边预览边保存视频,音频和图片

基于微软的DirectShow.dll的二次开发1.自动识别连接的摄像头跟麦克风且可以对其进行选择(默认选中第一个)2.可录制wmv和avi两种格式的视频并且都带有音频,avi可以录制的分辨率和帧数进行选择,wmv默认进行了淸晰度优化如不喜欢可去除代码中有相关提示3.可在预览点开之后进行拍照,也可边录制视频边拍照4.添加了视频和音频的压缩功能(酌情使用)这次二次开发发现C#对DirectShow的相关信息太少,这次做完也不敢藏私共享出来,还望大家指正

YOLO12模型切换指南:如何更换不同大小模型

本文介绍了如何在星图GPU平台上自动化部署YOLO12 目标检测模型 WebUI镜像,快速构建可切换多尺寸模型的目标检测服务。用户无需手动配置环境,即可基于WebUI对图片或视频流执行实时目标检测,典型应用于工业质检、交通监控与安防分析等场景,显著提升AI检测落地效率。

weixin_36487018的博客 402

visio安装包

Microsoft Office Visio 是一款专业的制图软件。利用经过更新的形状、协作工具和数据链接图表,创建专业级图表以简化复杂的信息。

ssm框架搭建

这个是一个在idea上成功跑起来的ssm框架项目,保存在这里方便以后使用直接下载

Day 14 - 安装与执行 YOLO

Day 14 - 安装与执行 YOLO 在 介绍影像辨识的处理流程 - Day 10 有提到 YOLO 模型是由 Joseph Redmon 所提出,而到了 YOLOV4 后才换成另外一群人继续发展,YOLOV4 的作者是 Alexey Bochoknovskiy, Chien-Yao Wang, 与 Hong-Yuan Mark Liao,YOLOV5 的作者 Glenn Jocher。 安装 YOLO 今天会将 YOLOV3 安装在 Amazon Linux 2,首先从 Joseph Redmon 所建

m0_50614038的博客 1100

大中型超市收银系统(可直接运行)

光步前台收银系统系统功能:商品销售、商品退货、挂单、收银员权限、会员销售、单品取消、整单取消、商品查询、脱机销售、脱机数据上传,基本资料下载,开钱箱、小票打印、收款结算,支持多币种付款方式(现金、储值卡、礼券、微信等),支持多种促销。运行环境:.net 4.0登陆信息用户名:1001 密码:123456内置商品信息,商品编码可输入00001000 - 00010000,测试效果相关功能键F5 结算 F9挂单 F11商品查询 F8退货 Insert单品取消 Del整单取消 F12开钱箱F2 会员 Ctrl+Z退出系统 Home 锁屏 相关源码待公开

计算机视觉——day68:YOLO9000: Better, Faster, Stronger(未完结)

YOLO9000是一个通过联合优化检测和分类来检测9000多个对象类别的实时框架。我们使用WordTree联合收割机来自不同来源的数据,并使用联合优化技术在ImageNet和COCO上同时进行训练。YOLO9000是缩小检测和分类之间数据集大小差距的有力一步

想太多的学习日志 803

yolov8学习

yolov8下载和简单使用(对图片的detect和对coco128数据集的推理)

Mjy的博客 694
上一篇: 【已开源】mtcnn_pytorch完美复现
下一篇: YOLO系列解读DAY2—YOLOV1预测代码转换
samylee
博客等级 码龄11年 585粉丝 92原创
评论 6
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值