class_docstr: Side-Aware Boundary Localization (SABL) for RetinaNet.
  
  The anchor generation, assigning and sampling in SABLRetinaHead
  are the same as GuidedAnchorHead for guided anchoring.
  
  Please refer to https://arxiv.org/abs/1912.04260 for more details.
  
  Args:
      num_classes (int): Number of classes.
      in_channels (int): Number of channels in the input feature map.
      stacked_convs (int): Number of Convs for classification             and regression branches. Defaults to 4.
      feat_channels (int): Number of hidden channels.             Defaults to 256.
      approx_anchor_generator (dict): Config dict for approx generator.
      square_anchor_generator (dict): Config dict for square generator.
      conv_cfg (dict): Config dict for ConvModule. Defaults to None.
      norm_cfg (dict): Config dict for Norm Layer. Defaults to None.
      bbox_coder (dict): Config dict for bbox coder.
      reg_decoded_bbox (bool): Whether to regress decoded bbox.             Defaults to False.
      train_cfg (dict): Training config of SABLRetinaHead.
      test_cfg (dict): Testing config of SABLRetinaHead.
      loss_cls (dict): Config of classification loss.
      loss_bbox_cls (dict): Config of classification loss for bbox branch.
      loss_bbox_reg (dict): Config of regression loss for bbox branch.
code: def __init__(
      self,
      num_classes,
      in_channels,
      stacked_convs=4,
      feat_channels=256,
      approx_anchor_generator=dict(
          type="AnchorGenerator",
          octave_base_scale=4,
          scales_per_octave=3,
          ratios=[0.5, 1.0, 2.0],
          strides=[8, 16, 32, 64, 128],
      ),
      square_anchor_generator=dict(
          type="AnchorGenerator",
          ratios=[1.0],
          scales=[4],
          strides=[8, 16, 32, 64, 128],
      ),
      conv_cfg=None,
      norm_cfg=None,
      bbox_coder=dict(
          type="BucketingBBoxCoder", num_buckets=14, scale_factor=3.0
      ),
      reg_decoded_bbox=False,
      train_cfg=None,
      test_cfg=None,
      loss_cls=dict(
          type="FocalLoss",
          use_sigmoid=True,
          gamma=2.0,
          alpha=0.25,
          loss_weight=1.0,
      ),
      loss_bbox_cls=dict(
          type="CrossEntropyLoss", use_sigmoid=True, loss_weight=1.5
      ),
      loss_bbox_reg=dict(
          type="SmoothL1Loss", beta=1.0 / 9.0, loss_weight=1.5
      ),
  ):
      super(SABLRetinaHead, self).__init__()
      self.in_channels = in_channels
      self.num_classes = num_classes
      self.feat_channels = feat_channels
      self.num_buckets = bbox_coder["num_buckets"]
      self.side_num = int(np.ceil(self.num_buckets / 2))
  
      assert (
          approx_anchor_generator["octave_base_scale"]
          == square_anchor_generator["scales"][0]
      )
      assert (
          approx_anchor_generator["strides"]
          == square_anchor_generator["strides"]
      )
  
      self.approx_anchor_generator = build_anchor_generator(
          approx_anchor_generator
      )
      self.square_anchor_generator = build_anchor_generator(
          square_anchor_generator
      )
      self.approxs_per_octave = (
          self.approx_anchor_generator.num_base_anchors[0]
      )
  
      # one anchor per location
      self.num_anchors = 1
      self.stacked_convs = stacked_convs
      self.conv_cfg = conv_cfg
      self.norm_cfg = norm_cfg
  
      self.reg_decoded_bbox = reg_decoded_bbox
  
      self.use_sigmoid_cls = loss_cls.get("use_sigmoid", False)
      self.sampling = loss_cls["type"] not in [
          "FocalLoss",
          "GHMC",
          "QualityFocalLoss",
      ]
      if self.use_sigmoid_cls:
          self.cls_out_channels = num_classes
      else:
          self.cls_out_channels = num_classes + 1
  
      self.bbox_coder = build_bbox_coder(bbox_coder)
      self.loss_cls = build_loss(loss_cls)
      self.loss_bbox_cls = build_loss(loss_bbox_cls)
      self.loss_bbox_reg = build_loss(loss_bbox_reg)
  
      self.train_cfg = train_cfg
      self.test_cfg = test_cfg
  
      if self.train_cfg:
          self.assigner = build_assigner(self.train_cfg.assigner)
          # use PseudoSampler when sampling is False
          if self.sampling and hasattr(self.train_cfg, "sampler"):
              sampler_cfg = self.train_cfg.sampler
          else:
              sampler_cfg = dict(type="PseudoSampler")
          self.sampler = build_sampler(sampler_cfg, context=self)
  
      self.fp16_enabled = False
      self._init_layers()
  
imports: import numpy
  import torch
  import torch.nn
  from mmcv.cnn import ConvModule, bias_init_with_prob, normal_init
  from mmcv.runner import force_fp32
  from mmdet.core import build_anchor_generator, build_assigner, build_bbox_coder, build_sampler, images_to_levels, multi_apply, multiclass_nms, unmap
  from ..builder import HEADS, build_loss
  from .base_dense_head import BaseDenseHead
  from .guided_anchor_head import GuidedAnchorHead
label_desc: Use image node_id 1 to create a new SABLRetinaHead object from inherited base classes: BaseDenseHead with example: obj = SABLRetinaHead(num_classes, in_channels, stacked_convs, feat_channels, approx_anchor_generator, square_anchor_generator, conv_cfg, norm_cfg, bbox_coder, reg_decoded_bbox, train_cfg, test_cfg, loss_cls, loss_bbox_cls, loss_bbox_reg)