open-mmlab/mmdetection · error · RuntimeError

DETR do not build sampler.

Error message

DETR do not build sampler.

What it means

DETRHead.__init__ raises RuntimeError if train_cfg contains a 'sampler' entry. DETR uses hungarian (one-to-one) bipartite matching via the assigner only; a positive/negative sampler is meaningless and its presence indicates a misconfigured head.

Source

Thrown at mmdet/models/dense_heads/detr_head.py:105

            bg_cls_weight = loss_cls.get('bg_cls_weight', class_weight)
            assert isinstance(bg_cls_weight, float), 'Expected ' \
                'bg_cls_weight to have type float. Found ' \
                f'{type(bg_cls_weight)}.'
            class_weight = torch.ones(num_classes + 1) * class_weight
            # set background class as the last indice
            class_weight[num_classes] = bg_cls_weight
            loss_cls.update({'class_weight': class_weight})
            if 'bg_cls_weight' in loss_cls:
                loss_cls.pop('bg_cls_weight')
            self.bg_cls_weight = bg_cls_weight

        if train_cfg:
            assert 'assigner' in train_cfg, 'assigner should be provided ' \
                                            'when train_cfg is set.'
            assigner = train_cfg['assigner']
            self.assigner = TASK_UTILS.build(assigner)
            if train_cfg.get('sampler', None) is not None:
                raise RuntimeError('DETR do not build sampler.')
        self.num_classes = num_classes
        self.embed_dims = embed_dims
        self.num_reg_fcs = num_reg_fcs
        self.train_cfg = train_cfg
        self.test_cfg = test_cfg
        self.loss_cls = MODELS.build(loss_cls)
        self.loss_bbox = MODELS.build(loss_bbox)
        self.loss_iou = MODELS.build(loss_iou)

        if self.loss_cls.use_sigmoid:
            self.cls_out_channels = num_classes
        else:
            self.cls_out_channels = num_classes + 1

        self._init_layers()

    def _init_layers(self) -> None:
        """Initialize layers of the transformer head."""

View on GitHub (pinned to cfd5d3a985)

Solutions

  1. Remove the 'sampler' key (or set it to None) from train_cfg for DETR heads
  2. Keep only 'assigner' (HungarianAssigner) in train_cfg

Example fix

// before
train_cfg=dict(assigner=dict(type='HungarianAssigner'), sampler=dict(type='PseudoSampler'))
// after
train_cfg=dict(assigner=dict(type='HungarianAssigner'), sampler=None)
Defensive patterns

Strategy: validation

Validate before calling

if train_cfg:\n    assert train_cfg.get('sampler') is None, 'DETR heads must not define a sampler'

Prevention

When it happens

Trigger: Copying a train_cfg with a RandomSampler/PseudoSampler block (from an anchor-based head like RetinaNet/ATSS) into a DETR config; leftover sampler key after converting a config to DETR.

Common situations: Reusing RPN or RCNN head train_cfg in DETR-style heads; editing configs from anchor-based models.

Understand the failure class

Background: "Invalid value" and "allowed values are" config errors: what your library rejected and how to fix it — this error's family across 41 libraries.

Related errors


AI-assisted analysis of open-mmlab/mmdetection@cfd5d3a985 (2026-08-27). Data as JSON: /api/errors/0843636d55f3a5df. Report an issue: GitHub.