Browse Source

rename YOLOv7-Plus to YOLOv5-Plus

yjh0410 2 years ago
parent
commit
235b012730

+ 4 - 4
config/__init__.py

@@ -5,7 +5,7 @@ from .yolov3_config import yolov3_cfg
 from .yolov4_config import yolov4_cfg
 from .yolov5_config import yolov5_cfg
 from .yolov7_config import yolov7_cfg
-from .yolov7_plus_config import yolov7_plus_cfg
+from .yolov5_plus_config import yolov5_plus_cfg
 from .yolox_config import yolox_cfg
 
 
@@ -27,12 +27,12 @@ def build_model_config(args):
     # YOLOv5
     elif args.model in ['yolov5_n', 'yolov5_s', 'yolov5_m', 'yolov5_l', 'yolov5_x']:
         cfg = yolov5_cfg[args.model]
+    # YOLOv5-Plus
+    elif args.model in ['yolov5_plus_n', 'yolov5_plus_s', 'yolov5_plus_m', 'yolov5_plus_l', 'yolov5_plus_x']:
+        cfg = yolov5_plus_cfg[args.model]
     # YOLOv7
     elif args.model in ['yolov7_t', 'yolov7_l', 'yolov7_x']:
         cfg = yolov7_cfg[args.model]
-    # YOLOv8
-    elif args.model in ['yolov7_plus_n', 'yolov7_plus_s', 'yolov7_plus_m', 'yolov7_plus_l', 'yolov7_plus_x']:
-        cfg = yolov7_plus_cfg[args.model]
     # YOLOX
     elif args.model == 'yolox':
         cfg = yolox_cfg

+ 12 - 12
config/yolov7_plus_config.py → config/yolov5_plus_config.py

@@ -1,7 +1,7 @@
 # yolov8 config
 
-yolov7_plus_cfg = {
-    'yolov7_plus_n':{
+yolov5_plus_cfg = {
+    'yolov5_plus_n':{
         # input
         'trans_type': 'yolov5_tiny',
         'multi_scale': [0.5, 1.0],   # 320 -> 640
@@ -24,7 +24,7 @@ yolov7_plus_cfg = {
         'neck_norm': 'BN',
         'neck_depthwise': False,
         ## Neck: FPN
-        'fpn': 'yolov7_plus_pafpn',
+        'fpn': 'yolov5_plus_pafpn',
         'fpn_reduce_layer': 'Conv',
         'fpn_downsample_layer': 'Conv',
         'fpn_core_block': 'ELAN_CSPBlock',
@@ -73,7 +73,7 @@ yolov7_plus_cfg = {
         'warmup_bias_lr': 0.1,
     },
 
-    'yolov7_plus_s':{
+    'yolov5_plus_s':{
         # input
         'trans_type': 'yolov5_small',
         'multi_scale': [0.5, 1.0],   # 320 -> 640
@@ -96,7 +96,7 @@ yolov7_plus_cfg = {
         'neck_norm': 'BN',
         'neck_depthwise': False,
         # Neck: FPN
-        'fpn': 'yolov7_plus_pafpn',
+        'fpn': 'yolov5_plus_pafpn',
         'fpn_reduce_layer': 'Conv',
         'fpn_downsample_layer': 'Conv',
         'fpn_core_block': 'ELAN_CSPBlock',
@@ -145,7 +145,7 @@ yolov7_plus_cfg = {
         'warmup_bias_lr': 0.1,
     },
 
-    'yolov7_plus_m':{
+    'yolov5_plus_m':{
         # input
         'trans_type': 'yolov5_medium',
         'multi_scale': [0.5, 1.0],   # 320 -> 640
@@ -168,7 +168,7 @@ yolov7_plus_cfg = {
         'neck_norm': 'BN',
         'neck_depthwise': False,
         # Neck: FPN
-        'fpn': 'yolov7_plus_pafpn',
+        'fpn': 'yolov5_plus_pafpn',
         'fpn_reduce_layer': 'Conv',
         'fpn_downsample_layer': 'Conv',
         'fpn_core_block': 'ELAN_CSPBlock',
@@ -217,7 +217,7 @@ yolov7_plus_cfg = {
         'warmup_bias_lr': 0.1,
     },
 
-    'yolov7_plus_l':{
+    'yolov5_plus_l':{
         # input
         'trans_type': 'yolov5_large',
         'multi_scale': [0.5, 1.0],   # 320 -> 640
@@ -240,7 +240,7 @@ yolov7_plus_cfg = {
         'neck_norm': 'BN',
         'neck_depthwise': False,
         # Neck: FPN
-        'fpn': 'yolov7_plus_pafpn',
+        'fpn': 'yolov5_plus_pafpn',
         'fpn_reduce_layer': 'Conv',
         'fpn_downsample_layer': 'Conv',
         'fpn_core_block': 'ELAN_CSPBlock',
@@ -289,14 +289,14 @@ yolov7_plus_cfg = {
         'warmup_bias_lr': 0.1,
     },
 
-    'yolov7_plus_x':{
+    'yolov5_plus_x':{
         # input
         'trans_type': 'yolov5_huge',
         'multi_scale': [0.5, 1.0],   # 320 -> 640
         # ----------------- Model config 
         # Backbone
         'backbone': 'elan_cspnet',
-        'pretrained': True,
+        'pretrained': False,
         'bk_act': 'silu',
         'bk_norm': 'BN',
         'bk_dpw': False,
@@ -312,7 +312,7 @@ yolov7_plus_cfg = {
         'neck_norm': 'BN',
         'neck_depthwise': False,
         # Neck: FPN
-        'fpn': 'yolov7_plus_pafpn',
+        'fpn': 'yolov5_plus_pafpn',
         'fpn_reduce_layer': 'Conv',
         'fpn_downsample_layer': 'Conv',
         'fpn_core_block': 'ELAN_CSPBlock',

+ 4 - 4
models/detectors/__init__.py

@@ -8,7 +8,7 @@ from .yolov3.build import build_yolov3
 from .yolov4.build import build_yolov4
 from .yolov5.build import build_yolov5
 from .yolov7.build import build_yolov7
-from .yolov7_plus.build import build_yolov7_plus
+from .yolov5_plus.build import build_yolov5_plus
 from .yolox.build import build_yolox
 
 
@@ -42,9 +42,9 @@ def build_model(args,
     elif args.model in ['yolov7_t', 'yolov7_l', 'yolov7_x']:
         model, criterion = build_yolov7(
             args, model_cfg, device, num_classes, trainable)
-    # YOLOv7-Plus
-    elif args.model in ['yolov7_plus_n', 'yolov7_plus_s', 'yolov7_plus_m', 'yolov7_plus_l', 'yolov7_plus_x']:
-        model, criterion = build_yolov7_plus(
+    # YOLOv5-Plus
+    elif args.model in ['yolov5_plus_n', 'yolov5_plus_s', 'yolov5_plus_m', 'yolov5_plus_l', 'yolov5_plus_x']:
+        model, criterion = build_yolov5_plus(
             args, model_cfg, device, num_classes, trainable)
     # YOLOX   
     elif args.model == 'yolox':

+ 3 - 3
models/detectors/yolov7_plus/build.py → models/detectors/yolov5_plus/build.py

@@ -5,11 +5,11 @@ import torch
 import torch.nn as nn
 
 from .loss import build_criterion
-from .yolov7_plus import YOLOv7_Plus
+from .yolov5_plus import YOLOv5_Plus
 
 
 # build object detector
-def build_yolov7_plus(args, cfg, device, num_classes=80, trainable=False):
+def build_yolov5_plus(args, cfg, device, num_classes=80, trainable=False):
     print('==============================')
     print('Build {} ...'.format(args.model.upper()))
     
@@ -17,7 +17,7 @@ def build_yolov7_plus(args, cfg, device, num_classes=80, trainable=False):
     print('Model Configuration: \n', cfg)
     
     # -------------- Build YOLO --------------
-    model = YOLOv7_Plus(
+    model = YOLOv5_Plus(
         cfg=cfg,
         device=device, 
         num_classes=num_classes,

+ 7 - 5
models/detectors/yolov7_plus/loss.py → models/detectors/yolov5_plus/loss.py

@@ -194,12 +194,14 @@ class Criterion(object):
                                  'labels': [...], 
                                  'orig_size': ...}, ...]
         """
-        if epoch >= self.warmup_epoch:
-            print('Switch to Dynamic Label Assignment.')
-            self.warmup_stage = False
-
-        if self.warmup_stage:
+        # Fixed LA stage
+        if epoch < self.warmup_epoch:
             return self.fixed_assignment_loss(outputs, targets)
+        # Switch to Dynamic LA stage
+        elif epoch == self.warmup_epoch:
+            print('Switch to Dynamic Label Assignment.')
+            return self.dynamic_assignment_loss(outputs, targets)
+        # Dynamic LA stage
         else:
             return self.dynamic_assignment_loss(outputs, targets)
     

+ 0 - 0
models/detectors/yolov7_plus/matcher.py → models/detectors/yolov5_plus/matcher.py


+ 7 - 7
models/detectors/yolov7_plus/yolov7_plus.py → models/detectors/yolov5_plus/yolov5_plus.py

@@ -2,16 +2,16 @@ import torch
 import torch.nn as nn
 import torch.nn.functional as F
 
-from .yolov7_plus_backbone import build_backbone
-from .yolov7_plus_neck import build_neck
-from .yolov7_plus_pafpn import build_fpn
-from .yolov7_plus_head import build_head
+from .yolov5_plus_backbone import build_backbone
+from .yolov5_plus_neck import build_neck
+from .yolov5_plus_pafpn import build_fpn
+from .yolov5_plus_head import build_head
 
 from utils.misc import multiclass_nms
 
 
-# Anchor-free YOLO
-class YOLOv7_Plus(nn.Module):
+# Stronger YOLOv5
+class YOLOv5_Plus(nn.Module):
     def __init__(self, 
                  cfg,
                  device, 
@@ -20,7 +20,7 @@ class YOLOv7_Plus(nn.Module):
                  nms_thresh = 0.6,
                  trainable = False, 
                  topk = 1000):
-        super(YOLOv7_Plus, self).__init__()
+        super(YOLOv5_Plus, self).__init__()
         # --------- Basic Parameters ----------
         self.cfg = cfg
         self.device = device

+ 2 - 2
models/detectors/yolov7_plus/yolov7_plus_backbone.py → models/detectors/yolov5_plus/yolov5_plus_backbone.py

@@ -2,9 +2,9 @@ import torch
 import torch.nn as nn
 
 try:
-    from .yolov7_plus_basic import Conv, ELAN_CSP_Block
+    from .yolov5_plus_basic import Conv, ELAN_CSP_Block
 except:
-    from yolov7_plus_basic import Conv, ELAN_CSP_Block
+    from yolov5_plus_basic import Conv, ELAN_CSP_Block
 
 
 # ---------------------------- ImageNet pretrained weights ----------------------------

+ 0 - 0
models/detectors/yolov7_plus/yolov7_plus_basic.py → models/detectors/yolov5_plus/yolov5_plus_basic.py


+ 2 - 66
models/detectors/yolov7_plus/yolov7_plus_head.py → models/detectors/yolov5_plus/yolov5_plus_head.py

@@ -1,9 +1,7 @@
 import torch
 import torch.nn as nn
-try:
-    from .yolov7_plus_basic import Conv
-except:
-    from yolov7_plus_basic import Conv
+
+from .yolov5_plus_basic import Conv
 
 
 class DecoupledHead(nn.Module):
@@ -35,7 +33,6 @@ class DecoupledHead(nn.Module):
                         norm_type=self.norm_type,
                         depthwise=cfg['head_depthwise'])
                         )
-                
         # reg head
         reg_feats = []
         self.reg_out_dim = out_dim
@@ -74,64 +71,3 @@ def build_head(cfg, in_dim, max_dim, num_classes=80):
     head = DecoupledHead(cfg, in_dim, max_dim, num_classes) 
 
     return head
-
-
-if __name__ == '__main__':
-    import time
-    from thop import profile
-    cfg = {
-        'num_cls_head': 2,
-        'num_reg_head': 2,
-        'head_act': 'silu',
-        'head_norm': 'BN',
-        'head_depthwise': False,
-        'reg_max': 16,
-    }
-    fpn_dims = [256, 512, 512]
-    # Head-1
-    model = build_head(cfg, 256, fpn_dims, num_classes=80)
-    x = torch.randn(1, 256, 80, 80)
-    t0 = time.time()
-    outputs = model(x)
-    t1 = time.time()
-    print('Time: ', t1 - t0)
-    # for out in outputs:
-    #     print(out.shape)
-
-    print('==============================')
-    flops, params = profile(model, inputs=(x, ), verbose=False)
-    print('==============================')
-    print('Head-1: GFLOPs : {:.2f}'.format(flops / 1e9 * 2))
-    print('Head-1: Params : {:.2f} M'.format(params / 1e6))
-
-    # Head-2
-    model = build_head(cfg, 512, fpn_dims, num_classes=80)
-    x = torch.randn(1, 512, 40, 40)
-    t0 = time.time()
-    outputs = model(x)
-    t1 = time.time()
-    print('Time: ', t1 - t0)
-    # for out in outputs:
-    #     print(out.shape)
-
-    print('==============================')
-    flops, params = profile(model, inputs=(x, ), verbose=False)
-    print('==============================')
-    print('Head-2: GFLOPs : {:.2f}'.format(flops / 1e9 * 2))
-    print('Head-2: Params : {:.2f} M'.format(params / 1e6))
-
-    # Head-3
-    model = build_head(cfg, 512, fpn_dims, num_classes=80)
-    x = torch.randn(1, 512, 20, 20)
-    t0 = time.time()
-    outputs = model(x)
-    t1 = time.time()
-    print('Time: ', t1 - t0)
-    # for out in outputs:
-    #     print(out.shape)
-
-    print('==============================')
-    flops, params = profile(model, inputs=(x, ), verbose=False)
-    print('==============================')
-    print('Head-3: GFLOPs : {:.2f}'.format(flops / 1e9 * 2))
-    print('Head-3: Params : {:.2f} M'.format(params / 1e6))

+ 1 - 1
models/detectors/yolov7_plus/yolov7_plus_neck.py → models/detectors/yolov5_plus/yolov5_plus_neck.py

@@ -1,6 +1,6 @@
 import torch
 import torch.nn as nn
-from .yolov7_plus_basic import Conv
+from .yolov5_plus_basic import Conv
 
 
 # Spatial Pyramid Pooling - Fast (SPPF) layer for YOLOv5 by Glenn Jocher

+ 9 - 8
models/detectors/yolov7_plus/yolov7_plus_pafpn.py → models/detectors/yolov5_plus/yolov5_plus_pafpn.py

@@ -2,17 +2,18 @@ import torch
 import torch.nn as nn
 import torch.nn.functional as F
 
-from .yolov7_plus_basic import (Conv, build_reduce_layer, build_downsample_layer, build_fpn_block)
+from .yolov5_plus_basic import (Conv, build_reduce_layer, build_downsample_layer, build_fpn_block)
 
 
 # YOLO-Style PaFPN
-class Yolov7PlusPaFPN(nn.Module):
+class Yolov5PlusPaFPN(nn.Module):
     def __init__(self, cfg, in_dims=[256, 512, 1024], out_dim=None):
-        super(Yolov7PlusPaFPN, self).__init__()
+        super(Yolov5PlusPaFPN, self).__init__()
         # --------------------------- Basic Parameters ---------------------------
         self.in_dims = in_dims
         c3, c4, c5 = in_dims
         width = cfg['width']
+        ratio = cfg['ratio']
 
         # --------------------------- Network Parameters ---------------------------
         ## top dwon
@@ -31,19 +32,19 @@ class Yolov7PlusPaFPN(nn.Module):
 
         ### P4 -> P5
         self.downsample_layer_2 = build_downsample_layer(cfg, round(512*width), round(512*width))
-        self.bottom_up_layer_2 = build_fpn_block(cfg, round(512*width) + round(512*width), round(1024*width))
+        self.bottom_up_layer_2 = build_fpn_block(cfg, round(512*width) + round(512*width), round(512*width*ratio))
                 
         ## output proj layers
         if out_dim is not None:
             self.out_layers = nn.ModuleList([
                 Conv(in_dim, out_dim, k=1,
                      act_type=cfg['fpn_act'], norm_type=cfg['fpn_norm'])
-                     for in_dim in [round(256*width), round(512*width), round(1024*width)]
+                     for in_dim in [round(256*width), round(512*width), round(512*width*ratio)]
                      ])
             self.out_dim = [out_dim] * 3
         else:
             self.out_layers = None
-            self.out_dim = [round(256*width), round(512*width), round(1024*width)]
+            self.out_dim = [round(256*width), round(512*width), round(512*width*ratio)]
 
 
     def forward(self, features):
@@ -86,7 +87,7 @@ class Yolov7PlusPaFPN(nn.Module):
 def build_fpn(cfg, in_dims, out_dim=None):
     model = cfg['fpn']
     # build pafpn
-    if model == 'yolov7_plus_pafpn':
-        fpn_net = Yolov7PlusPaFPN(cfg, in_dims, out_dim)
+    if model == 'yolov5_plus_pafpn':
+        fpn_net = Yolov5PlusPaFPN(cfg, in_dims, out_dim)
 
     return fpn_net

+ 1 - 1
train.sh

@@ -3,7 +3,7 @@ python train.py \
         --cuda \
         -d coco \
         --root /mnt/share/ssd2/dataset/ \
-        -m yolov7_plus_n \
+        -m yolov5_plus_n \
         -bs 16 \
         -size 640 \
         --wp_epoch 1 \