YOLO多尺度测试,原图像太大,拆分

最近在做罂粟检测的项目,无人机从低空拍摄的图像较大,大概为5500*4500pix,直接用训练好的模型测试时,发现很多误检,同时很多可疑目标也没有检测到,用多尺度测试时,效果便较好了,代码如下:

import os
import cv2
from tqdm import tqdm


def get_imgs_pos(img_w, img_h, cut_w, cut_h, w_stride, h_stride):
    imgs_pos = []
    for beg_w in range(0, img_w, w_stride):
        for beg_h in range(0, img_h, h_stride):
            x0, y0 = beg_w, beg_h  # 左上角的点
            x1, y1 = beg_w + cut_w, beg_h + cut_h
            if x1 > img_w:  # x轴上超出图像边界
                x1 = img_w
                x0 = img_w - cut_w
            if y1 > img_h: # y轴上超出图像边界
                y1 = img_h
                y0 = img_h - cut_h
            imgs_pos.append([x0, y0, x1, y1])
            if y1 == img_h:  # 如果超出边界
                break
    return imgs_pos


def save_subimg(cv_img, pos, img_save_dir, img_name, idx):
    x0, y0, x1, y1 = pos
    crop_img = cv_img[y0:y1, x0:x1]
    cv2.imwrite(os.path.join(img_save_dir, img_name[0:-4] + "_" + "{:04d}".format(idx) + ".jpg"), crop_img)


def save_sublabs(sub_labels, label_save_dir, img_name, idx):
    lab_path = os.path.join(label_save_dir, img_name[0:-4] + "_" + "{:04d}".format(idx) + ".txt")
    with open(lab_path, 'w') as fw:
        for lab in sub_labels:
            line = " ".join(str(num) for num in lab)
            fw.write(line + "\n")



def read_labels(txt_path):
    pos = []
    with open(txt_path, 'r') as file_to_read:
        while True:
            lines = file_to_read.readline()  # 整行读取数据
            if not lines:
                break
                pass
            p_tmp = [float(i) for i in lines.split(' ')] 
            pos.append(p_tmp)  # 添加新读取的数据
            pass
    return pos


def get_sublabels(pos, labels, img_w, img_h, cut_w, cut_h):
    x0, y0, x1, y1 = pos  # 得到该子图在大图上的位置,左上角和右下角的坐标
    sub_labs = []
    for lab in labels:
        cx, cy, w, h = lab[1] * img_w, lab[2] * img_h, lab[3] * img_w, lab[4] * img_h  # 换算得到真实的中心点及宽高,注意第一个是标签的类别
        if x0 < cx < x1 and y0 < cy < y1:  # 如果该标签的中心点落到了子图上
            # 如果当前的标签落到了子图像的边界上, 处理该标签在子图上的宽的问题
            if cx - x0 < w / 2: 
                w = w / 2 + (cx - x0)
            if x1 - cx < w / 2:
                w = w / 2 + (x1 - cx)
            # 如果当前的标签落到了子图像的边界上, 处理该标签在子图上的高的问题
            if cy - y0 < h / 2:
                h = h / 2 + (cy - y0)
            if y1 - cy < h / 2:
                h = h / 2 + (y1 - cy)
            cx, cy = cx - x0, cy - y0  #  将当前的坐标换算到子图上(宽高不变,只是中心点的位置发生了改变)
            sub_labs.append([int(lab[0]), cx / cut_w, cy / cut_h, w / cut_w, h / cut_h])  #重新归一化  
    return sub_labs

if __name__ == '__main__':
    img_dir = "/data/jjg/codes/yolov5-5.0/data/poppy/419/images/"
    img_list = os.listdir(img_dir)
    img_save_dir = "/data/jjg/codes/yolov5-5.0/data/poppy/419/images_split"

    cut_w = 1920  # =1280*1.25
    cut_h = 1080
    w_stride = 1800
    h_stride = 1000
    count = 0
    for img_name in tqdm(img_list):
        sub_count = 0
        if img_name.endswith((".jpg", ".JPG")):
            img_path = os.path.join(img_dir, img_name)
            cv_img = cv2.imread(img_path, cv2.IMREAD_UNCHANGED)
            img_w, img_h = cv_img.shape[1], cv_img.shape[0]
            if img_w > cut_w and img_h > cut_h: # 如果原图的大小是大于需要裁剪的图像大小
                imgs_pos = get_imgs_pos(img_w, img_h, cut_w, cut_h, w_stride, h_stride)
                if len(imgs_pos):  # 如果原图像被拆分为了多个子图像
                    for idx, pos in enumerate(imgs_pos):  # 逐个对所有子图像寻找其图上的子lables
                        sub_count += 1
                        save_subimg(cv_img, pos, img_save_dir, img_name, idx)  # 保存该子图像
        # break
        # print(img_name, "has generated", count, "images.")
        count += sub_count
    print("Generate total images is:", count)

检测效果:

原图:(原图上中间偏上的可以目标没检测到,但是下面的图像中就能检测到)

 

拆分后的某一张:

 

  • 1
    点赞
  • 22
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
YOLO算法中,多尺度改进的目的是提高对不同尺度目标的检测精度和泛化能力。以下是一些常见的多尺度改进方法: 1. 图像金字塔(Image Pyramid):通过将输入图像按照不同的尺度进行缩放,然后分别输入到YOLO模型中进行检测。这样可以在不同尺度下对目标进行检测,从而提高对小目标的检测效果。 2. 多尺度训练(Multi-scale Training):在训练过程中,随机选择不同的尺度进行训练样本的缩放和裁剪。这样可以使模型学习到不同尺度目标的特征表示,提高模型的泛化能力。 3. 多尺度预测(Multi-scale Inference):在测试过程中,将输入图像按照不同的尺度进行缩放,然后分别输入到YOLO模型中进行检测。最后,将不同尺度下的检测结果进行融合,得到最终的检测结果。 4. 特征金字塔网络(Feature Pyramid Network,FPN):在YOLO网络中引入了多个特征金字塔层,每个层级都可以提供不同尺度的特征表示。这样可以在不同尺度上提取和融合多尺度的特征信息,提高对不同尺度目标的检测性能。 5. 多尺度Anchor Boxes:通过在不同尺度下使用不同大小和宽高比的Anchor Boxes,可以更好地适应不同尺度目标的特征。这样可以提高对小目标和大目标的检测精度。 这些方法可以单独或组合使用,根据具体任务和需求来选择和调整。通过多尺度改进,YOLO算法可以更好地适应不同尺度目标的检测需求,提高检测性能和泛化能力。
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值