def proposal_layer(rpn_cls_prob, rpn_bbox_pred, kpoints_pred, im_info, cfg_key, _feat_stride, anchors, num_anchors): """A simplified version compared to fast/er RCNN For details please see the technical report """ if type(cfg_key) == bytes: cfg_key = cfg_key.decode('utf-8') pre_nms_topN = cfg[cfg_key].RPN_PRE_NMS_TOP_N post_nms_topN = cfg[cfg_key].RPN_POST_NMS_TOP_N nms_thresh = cfg[cfg_key].RPN_NMS_THRESH min_size = cfg[cfg_key].ANCHOR_MIN_SIZE # Get the scores and bounding boxes scores = rpn_cls_prob[:, :, :, num_anchors:] rpn_bbox_pred = rpn_bbox_pred.reshape((-1, 4)) scores = scores.reshape((-1, 1)) proposals = bbox_transform_inv(anchors, rpn_bbox_pred) proposals = clip_boxes(proposals, im_info[:2]) # Get the facial landmarks kpoints_pred = kpoints_pred.reshape(-1, 10) points = kpoints_transform_inv(anchors, kpoints_pred) points = clip_kpoints(points, im_info[:2]) # removed predicted boxes with either height or width < threshold # (NOTE: convert min_size to input image scale stored in im_info[2]) keep = _filter_boxes(proposals, min_size * im_info[2]) proposals = proposals[keep, :] scores = scores[keep] points = points[keep] # Pick the top region proposals order = scores.ravel().argsort()[::-1] if pre_nms_topN > 0: order = order[:pre_nms_topN] proposals = proposals[order, :] scores = scores[order] points = points[order] # Non-maximal suppression keep = nms(np.hstack((proposals, scores)), nms_thresh) # Pick th top region proposals after NMS if post_nms_topN > 0: keep = keep[:post_nms_topN] proposals = proposals[keep, :] scores = scores[keep] points = points[keep] # Only support single image as input batch_inds = np.zeros((proposals.shape[0], 1), dtype=np.float32) blob = np.hstack((batch_inds, proposals.astype(np.float32, copy=False))) return blob, scores, points
def proposal_layer(rpn_cls_prob, rpn_bbox_pred, im_info, cfg_key, _feat_stride, anchors, num_anchors): """ rpn_cls_prob = [n, h, w, c=a*2] rpn_bbox_pred = [n, h, w, c=4*a] """ if type(cfg_key) == bytes: cfg_key = cfg_key.decode('utf-8') pre_nms_topN = cfg[cfg_key].RPN_PRE_NMS_TOP_N post_nms_topN = cfg[cfg_key].RPN_POST_NMS_TOP_N nms_thresh = cfg[cfg_key].RPN_NMS_THRESH # Get the scores and bounding boxes # 0:num_anchors is the probability of BG scores = rpn_cls_prob[:, :, :, num_anchors:] bbox_deltas = rpn_bbox_pred.view((-1, 4)) scores = scores.contiguous().view((-1, 1)) # 1.Convert anchors into proposals via bbox transformations proposals = bbox_transform_inv(anchors, bbox_deltas) # 2.clip predicted boxes to image proposals = clip_boxes(proposals, im_info[:2]) # # 3.remove predicted boxes with either height or width < threshold # # (NOTE: convert min_size to input image scale stored in im_info[2]) # keep = _filter_boxes(proposals, _feat_stride[0] * im_info[2]) # proposals = proposals[keep, :] # scores = scores[keep] # 4.sort all (proposal, score) pairs by score from highest to lowest # 5.take top pre_nms_topN (e.g. Train12000 Test6000) _, order = scores.view(-1).sort(descending=True) if pre_nms_topN > 0: order = order[:pre_nms_topN] proposals = proposals[order.data, :] scores = scores[order.data, :] # 6.Non-maximal suppression apply nms (e.g. threshold = 0.7) keep = nms(torch.cat((proposals, scores), 1).data, nms_thresh) # 7.Pick th top region proposals after NMS (e.g. Train2000 Test300) if post_nms_topN > 0: keep = keep[:post_nms_topN] proposals = proposals[keep, :] scores = scores[keep, :] # 8.Only support single image as input batch_inds = Variable(proposals.data.new(proposals.size(0), 1).zero_()) blob = torch.cat((batch_inds, proposals), 1) del batch_inds return blob, scores
def proposal_top_layer_batch(rpn_cls_probs, rpn_bbox_preds, im_info, _feat_stride, anchors, num_anchors, network_device): """A layer that just selects the top region proposals without using non-maximal suppression, For details please see the technical report """ rpn_top_n = cfg.TEST.RPN_TOP_N scores = rpn_cls_probs[:, :, :, num_anchors:] rpn_bbox_preds = rpn_bbox_preds.view(rpn_bbox_preds.size(0), -1, 4) scores = scores.contiguous().view(rpn_bbox_preds.size(0), -1, 1) blobs, scoress = [], [] for i in range(scores.size(0)): score = scores[i] length = score.size(0) if length < rpn_top_n: # Random selection, maybe unnecessary and loses good proposals # But such case rarely happens top_inds = torch.from_numpy( npr.choice(length, size=rpn_top_n, replace=True)).long().cuda(network_device) else: top_inds = score.sort(0, descending=True)[1] top_inds = top_inds[:rpn_top_n] top_inds = top_inds.view(rpn_top_n) # Do the selection here anchor = anchors[top_inds, :].contiguous() rpn_bbox_pred = rpn_bbox_preds[i][top_inds, :].contiguous() score = score[top_inds].contiguous() # Convert anchors into proposals via bbox transformations proposal = bbox_transform_inv(anchor, rpn_bbox_pred) # Clip predicted boxes to image proposal = clip_boxes(proposal, im_info[:2]) # Output rois blob # Our RPN implementation only supports a single input image, so all # batch inds are 0 batch_inds = proposal.new_zeros(proposal.size(0), 1) blob = torch.cat([batch_inds, proposal], 1) blobs.append(blob) scoress.append(score) return blobs, scoress
def proposal_layer(rpn_cls_prob, rpn_bbox_pred, im_info, cfg_key, _feat_stride, anchors, num_anchors): """A simplified version compared to fast/er RCNN For details please see the technical report """ if type(cfg_key) == bytes: cfg_key = cfg_key.decode('utf-8') pre_nms_topN = cfg[cfg_key].RPN_PRE_NMS_TOP_N post_nms_topN = cfg[cfg_key].RPN_POST_NMS_TOP_N nms_thresh = cfg[cfg_key].RPN_NMS_THRESH # Get the scores and bounding boxes scores = rpn_cls_prob[:, :, :, num_anchors:] #每个anchor 有打分 rpn_bbox_pred = rpn_bbox_pred.reshape((-1, 4)) scores = scores.reshape((-1, 1)) proposals = bbox_transform_inv( anchors, rpn_bbox_pred ) #通过这个函数 把 anchor 转化成 proposal? 根据anchor 与 rpn_bbox 返回一个预测的 proposal proposals = clip_boxes(proposals, im_info[:2]) # Pick the top region proposals order = scores.ravel().argsort()[::-1] #筛选出 top_N的 proposal if pre_nms_topN > 0: order = order[:pre_nms_topN] proposals = proposals[order, :] scores = scores[order] # Non-maximal suppression keep = nms( np.hstack((proposals, scores)), nms_thresh ) #极大抑制算法 继续筛选proposal NMS threshold used on RPN proposals=0.7 重合度大于0.7视为同一类 # Pick th top region proposals after NMS if post_nms_topN > 0: keep = keep[:post_nms_topN] proposals = proposals[keep, :] scores = scores[keep] #挑选 排序最好的 几个proposal # Only support single image as input batch_inds = np.zeros((proposals.shape[0], 1), dtype=np.float32) blob = np.hstack( (batch_inds, proposals.astype(np.float32, copy=False))) #返回 proposal 列表 return blob, scores
def proposal_layer_batch(rpn_cls_prob, rpn_bbox_pred, im_info, cfg_key, _feat_stride, anchors, num_anchors, network_device): """A simplified version compared to fast/er RCNN For details please see the technical report """ if type(cfg_key) == bytes: cfg_key = cfg_key.decode('utf-8') pre_nms_topN = cfg[cfg_key].RPN_PRE_NMS_TOP_N post_nms_topN = cfg[cfg_key].RPN_POST_NMS_TOP_N nms_thresh = cfg[cfg_key].RPN_NMS_THRESH # Get the scores and bounding boxes scores = rpn_cls_prob[:, :, :, num_anchors:] rpn_bbox_pred = rpn_bbox_pred.view((rpn_bbox_pred.size(0), -1, 4)) scores = scores.contiguous().view(scores.size(0), -1, 1) proposals = bbox_transform_inv_batch(anchors, rpn_bbox_pred) #here bug proposals = list(map(lambda x: clip_boxes(x, im_info[:2]), proposals)) blobs, scoress = [], [] for i in range(scores.size(0)): # Pick the top region proposals score, order = scores[i].view(-1).sort(descending=True) if pre_nms_topN > 0: order = order[:pre_nms_topN] score = score[:pre_nms_topN].view(-1, 1) proposal = proposals[i][order.data, :] # Non-maximal suppression keep = nms_batch( torch.cat((proposal, score), 1).data, nms_thresh, network_device) # Pick th top region proposals after NMS if post_nms_topN > 0: keep = keep[:post_nms_topN] proposal = proposal[keep] score = score[keep] # Only support single image as input batch_inds = proposal.new_zeros(proposal.size(0), 1) blob = torch.cat((batch_inds, proposal), 1) blobs.append(blob) scoress.append(score) return blobs, scoress
def proposal_top_layer(rpn_cls_prob, rpn_bbox_pred, im_info, _feat_stride, anchors, num_anchors): """A layer that just selects the top region proposals without using non-maximal suppression, For details please see the technical report """ rpn_top_n = cfg.TEST.RPN_TOP_N im_info = im_info[0] scores = rpn_cls_prob[:, :, :, num_anchors:] rpn_bbox_pred = rpn_bbox_pred.reshape((-1, 4)) scores = scores.reshape((-1, 1)) length = scores.shape[0] if length < rpn_top_n: # Random selection, maybe unnecessary and loses good proposals # But such case rarely happens top_inds = npr.choice(length, size=rpn_top_n, replace=True) else: top_inds = scores.argsort(0)[::-1] top_inds = top_inds[:rpn_top_n] top_inds = top_inds.reshape(rpn_top_n, ) # Do the selection here anchors = anchors[top_inds, :] rpn_bbox_pred = rpn_bbox_pred[top_inds, :] scores = scores[top_inds] # Convert anchors into proposals via bbox transformations proposals = bbox_transform_inv(anchors, rpn_bbox_pred) # Clip predicted boxes to image proposals = clip_boxes(proposals, im_info[:2]) # Output rois blob # Our RPN implementation only supports a single input image, so all # batch inds are 0 batch_inds = np.zeros((proposals.shape[0], 1), dtype=np.float32) blob = np.hstack((batch_inds, proposals.astype(np.float32, copy=False))) return blob, scores
def proposal_layer(rpn_cls_prob, rpn_bbox_pred, im_info, cfg_key, _feat_stride, anchors, num_anchors): """A simplified version compared to fast/er RCNN For details please see the technical report """ if type(cfg_key) == bytes: cfg_key = cfg_key.decode('utf-8') pre_nms_topN = cfg[cfg_key].RPN_PRE_NMS_TOP_N post_nms_topN = cfg[cfg_key].RPN_POST_NMS_TOP_N nms_thresh = cfg[cfg_key].RPN_NMS_THRESH # Get the scores and bounding boxes scores = rpn_cls_prob[:, :, :, num_anchors:] rpn_bbox_pred = rpn_bbox_pred.view((-1, 4)) scores = scores.contiguous().view(-1, 1) proposals = bbox_transform_inv(anchors, rpn_bbox_pred) proposals = clip_boxes(proposals, im_info[:2]) # Pick the top region proposals scores, order = scores.view(-1).sort(descending=True) if pre_nms_topN > 0: order = order[:pre_nms_topN] scores = scores[:pre_nms_topN].view(-1, 1) proposals = proposals[order.data, :] # Non-maximal suppression keep = nms(proposals, scores.squeeze(1), nms_thresh) # Pick th top region proposals after NMS if post_nms_topN > 0: keep = keep[:post_nms_topN] proposals = proposals[keep, :] scores = scores[keep, ] # Only support single image as input batch_inds = proposals.new_zeros(proposals.size(0), 1) blob = torch.cat((batch_inds, proposals), 1) return blob, scores