MCPcopy Create free account
hub / github.com/Project-MONAI/MONAI / batched_nms

Function batched_nms

monai/data/box_utils.py:1162–1207  ·  view source on GitHub ↗

Performs non-maximum suppression in a batched fashion. Each labels value correspond to a category, and NMS will not be applied between elements of different categories. Adapted from https://github.com/MIC-DKFZ/nnDetection/blob/main/nndet/core/boxes/nms.py Args: boxes: boun

(
    boxes: NdarrayOrTensor,
    scores: NdarrayOrTensor,
    labels: NdarrayOrTensor,
    nms_thresh: float,
    max_proposals: int = -1,
    box_overlap_metric: Callable = box_iou,
)

Source from the content-addressed store, hash-verified

1160
1161
1162def batched_nms(
1163 boxes: NdarrayOrTensor,
1164 scores: NdarrayOrTensor,
1165 labels: NdarrayOrTensor,
1166 nms_thresh: float,
1167 max_proposals: int = -1,
1168 box_overlap_metric: Callable = box_iou,
1169) -> NdarrayOrTensor:
1170 """
1171 Performs non-maximum suppression in a batched fashion.
1172 Each labels value correspond to a category, and NMS will not be applied between elements of different categories.
1173
1174 Adapted from https://github.com/MIC-DKFZ/nnDetection/blob/main/nndet/core/boxes/nms.py
1175
1176 Args:
1177 boxes: bounding boxes, Nx4 or Nx6 torch tensor or ndarray. The box mode is assumed to be ``StandardMode``
1178 scores: prediction scores of the boxes, sized (N,). This function keeps boxes with higher scores.
1179 labels: indices of the categories for each one of the boxes. sized(N,), value range is (0, num_classes)
1180 nms_thresh: threshold of NMS. Discards all overlapping boxes with box_overlap > nms_thresh.
1181 max_proposals: maximum number of boxes it keeps.
1182 If ``max_proposals`` = -1, there is no limit on the number of boxes that are kept.
1183 box_overlap_metric: the metric to compute overlap between boxes.
1184
1185 Returns:
1186 Indexes of ``boxes`` that are kept after NMS.
1187 """
1188 # returns empty array if boxes is empty
1189 if boxes.shape[0] == 0:
1190 return convert_to_dst_type(src=np.array([]), dst=boxes, dtype=torch.long)[0]
1191
1192 # convert numpy to tensor if needed
1193 boxes_t, *_ = convert_data_type(boxes, torch.Tensor, dtype=torch.float32)
1194 scores_t, *_ = convert_to_dst_type(scores, boxes_t)
1195 labels_t, *_ = convert_to_dst_type(labels, boxes_t, dtype=torch.long)
1196
1197 # strategy: in order to perform NMS independently per class.
1198 # we add an offset to all the boxes. The offset is dependent
1199 # only on the class idx, and is large enough so that boxes
1200 # from different classes do not overlap
1201 max_coordinate = boxes_t.max()
1202 offsets = labels_t.to(boxes_t) * (max_coordinate + 1)
1203 boxes_for_nms = boxes + offsets[:, None]
1204 keep = non_max_suppression(boxes_for_nms, scores_t, nms_thresh, max_proposals, box_overlap_metric)
1205
1206 # convert tensor back to numpy if needed
1207 return convert_to_dst_type(src=keep, dst=boxes, dtype=keep.dtype)[0]

Callers 1

Calls 4

convert_to_dst_typeFunction · 0.90
convert_data_typeFunction · 0.90
non_max_suppressionFunction · 0.85
arrayMethod · 0.80

Tested by

no test coverage detected

Used in the wild real call sites across dependent graphs

searching dependent graphs…