Exemple #1
0
    def detect(self, img, threshold=0.5, scales=[1.0]):
        proposals_list = []
        landmarks_list = []
        scores_list = []

        for im_scale in scales:

            if im_scale != 1.0:
                im = cv2.resize(img,
                                None,
                                None,
                                fx=im_scale,
                                fy=im_scale,
                                interpolation=cv2.INTER_LINEAR)
            else:
                im = img
            im = im.astype(np.float32)
            # self.model.bind(data_shapes=[('data', (1, 3, image_size[0], image_size[1]))], for_training=False)
            im_info = [im.shape[0], im.shape[1], im_scale]
            im_tensor = np.zeros((1, 3, im.shape[0], im.shape[1]))
            for i in range(3):
                im_tensor[0,
                          i, :, :] = im[:, :, 2 - i] - self.pixel_means[2 - i]
            data = nd.array(im_tensor)
            db = mx.io.DataBatch(data=(data, ),
                                 provide_data=[('data', data.shape)])
            self.model.forward(db, is_train=False)
            net_out = self.model.get_outputs()
            pre_nms_topN = self._rpn_pre_nms_top_n
            # post_nms_topN = self._rpn_post_nms_top_n
            # min_size_dict = self._rpn_min_size_fpn

            for s in self._feat_stride_fpn:
                if len(scales) > 1 and s == 32 and im_scale == scales[-1]:
                    continue
                _key = 'stride%s' % s
                stride = int(s)
                idx = 0
                if s == 16:
                    idx = 3
                elif s == 8:
                    idx = 6
                # print('getting', im_scale, stride, idx, len(net_out), data.shape, file=sys.stderr)

                scores = net_out[idx].asnumpy()
                # print(scores.shape)
                idx += 1
                # print('scores',stride, scores.shape, file=sys.stderr)
                scores = scores[:, self._num_anchors['stride%s' % s]:, :, :]
                bbox_deltas = net_out[idx].asnumpy()
                idx += 1

                # if DEBUG:
                #    print 'im_size: ({}, {})'.format(im_info[0], im_info[1])
                #    print 'scale: {}'.format(im_info[2])

                _height, _width = int(im_info[0] / stride), int(im_info[1] /
                                                                stride)
                height, width = bbox_deltas.shape[2], bbox_deltas.shape[3]

                # kpoint
                kpoint_deltas = net_out[idx].asnumpy()

                A = self._num_anchors['stride%s' % s]
                K = height * width

                anchors = anchors_plane(
                    height, width, stride,
                    self._anchors_fpn['stride%s' % s].astype(np.float32))
                # print((height, width), (_height, _width), anchors.shape, bbox_deltas.shape, scores.shape, file=sys.stderr)
                anchors = anchors.reshape((K * A, 4))
                # print('pre', bbox_deltas.shape, height, width)
                bbox_deltas = self._clip_pad(bbox_deltas, (height, width))
                # print('after', bbox_deltas.shape, height, width)
                bbox_deltas = bbox_deltas.transpose((0, 2, 3, 1)).reshape(
                    (-1, 4))

                kpoint_deltas = self._clip_pad(kpoint_deltas, (height, width))
                kpoint_deltas = kpoint_deltas.transpose((0, 2, 3, 1)).reshape(
                    (-1, 10))

                scores = self._clip_pad(scores, (height, width))
                scores = scores.transpose((0, 2, 3, 1)).reshape((-1, 1))

                # print(anchors.shape, bbox_deltas.shape, A, K, file=sys.stderr)
                proposals = self._bbox_pred(anchors, bbox_deltas)
                # proposals = anchors

                proposals = clip_boxes(proposals, im_info[:2])

                landmarks = landmark_pred(anchors, kpoint_deltas)

                landmarks = clip_points(landmarks, im_info[:2])

                # keep = self._filter_boxes(proposals, min_size_dict['stride%s'%s] * im_info[2])
                # proposals = proposals[keep, :]
                # scores = scores[keep]
                # print('333', proposals.shape)

                scores_ravel = scores.ravel()
                order = scores_ravel.argsort()[::-1]
                if pre_nms_topN > 0:
                    order = order[:pre_nms_topN]
                proposals = proposals[order, :]
                landmarks = landmarks[order, :]
                scores = scores[order]

                proposals /= im_scale
                landmarks /= im_scale

                proposals_list.append(proposals)
                landmarks_list.append(landmarks)
                scores_list.append(scores)

        proposals = np.vstack(proposals_list)
        landmarks = np.vstack(landmarks_list)
        scores = np.vstack(scores_list)
        scores_ravel = scores.ravel()
        order = scores_ravel.argsort()[::-1]
        #if config.TEST.SCORE_THRESH>0.0:
        #  _count = np.sum(scores_ravel>config.TEST.SCORE_THRESH)
        #  order = order[:_count]
        #if pre_nms_topN > 0:
        #    order = order[:pre_nms_topN]
        proposals = proposals[order, :]
        landmarks = landmarks[order, :]
        scores = scores[order]

        det = np.hstack((proposals, scores, landmarks)).astype(np.float32)

        #if np.shape(det)[0] == 0:
        #    print("Something wrong with the input image(resolution is too low?), generate fake proposals for it.")
        #    proposals = np.array([[1.0, 1.0, 2.0, 2.0]]*post_nms_topN, dtype=np.float32)
        #    scores = np.array([[0.9]]*post_nms_topN, dtype=np.float32)
        #    det = np.array([[1.0, 1.0, 2.0, 2.0, 0.9]]*post_nms_topN, dtype=np.float32)

        if self.nms_threshold < 1.0:
            keep = self.nms(det)
            det = det[keep, :]
        if threshold > 0.0:
            keep = np.where(det[:, 4] >= threshold)[0]
            det = det[keep, :]
        return det
    def detect(self, img, threshold=0.5, scales=[1.0]):
        proposals_list = []
        proposals_kp_list = []
        scores_list = []

        for im_scale in scales:
            if im_scale != 1.0:
                im = cv2.resize(img, None, None, fx=im_scale, fy=im_scale, interpolation=cv2.INTER_LINEAR)
            else:
                im = img
            im = im.astype(np.float32)
            # im_shape = im.shape
            # self.model.bind(data_shapes=[('data', (1, 3, im_shape[0], im_shape[1]))], for_training=False)
            im_info = [im.shape[0], im.shape[1], im_scale]
            im_tensor = np.zeros((1, 3, im.shape[0], im.shape[1]))
            for i in range(3):
                im_tensor[0, i, :, :] = im[:, :, 2 - i] - self.pixel_means[2 - i] #bgr2rgb  mxnet rgb  opencv bgr
            data = nd.array(im_tensor)
            db = mx.io.DataBatch(data=(data,), provide_data=[('data', data.shape)])
            
            timea = datetime.datetime.now()
            self.model.forward(db, is_train=False)
            timeb = datetime.datetime.now()
            diff = timeb - timea
            print('forward uses', diff.total_seconds(), 'seconds')

            net_out = self.model.get_outputs()      #网络的输出为len=9的list,针对三个不同的stride,分为三大块的list,其中每个list分别代表score,bbox,kpoint三个维度的结果,
            pre_nms_topN = self._rpn_pre_nms_top_n
            #post_nms_topN = self._rpn_post_nms_top_n
            #min_size_dict = self._rpn_min_size_fpn

            for s in self.feat_strides:
                _key = 'stride%s' % s
                # print(_key)
                stride = int(s)
                if s == self.feat_strides[0]:
                    idx = 0
                if s == self.feat_strides[1]:
                    idx = 3
                elif s == self.feat_strides[2]:
                    idx = 6
                # print('getting', im_scale, stride, idx, len(net_out), data.shape, file=sys.stderr)
                scores = net_out[idx].asnumpy()     #获取每个stride下的分类得分

                idx += 1
                # print('scores',stride, scores.shape, file=sys.stderr)
                scores = scores[:, self._num_anchors['stride%s'%s]:, :, :]    #去掉了其中lable的值???
                bbox_deltas = net_out[idx].asnumpy()
                idx += 1
                _height, _width = int(im_info[0] / stride), int(im_info[1] / stride)
                height, width = bbox_deltas.shape[2], bbox_deltas.shape[3]

                # kpoint
                kpoint_deltas = net_out[idx].asnumpy()

                A = self._num_anchors['stride%s' % s]
                K = height * width
                anchors = anchors_plane(height, width, stride, self._anchors_fpn['stride%s' % s].astype(np.float32))       #RP映射回原图中的坐标位置
                # print((height, width), (_height, _width), anchors.shape, bbox_deltas.shape, scores.shape, file=sys.stderr)
                anchors = anchors.reshape((K * A, 4))

                # print('predict bbox_deltas', bbox_deltas.shape, height, width)
                bbox_deltas = self._clip_pad(bbox_deltas, (height, width))
                # print('after clip pad', bbox_deltas.shape, height, width)
                bbox_deltas = bbox_deltas.transpose((0, 2, 3, 1)).reshape((-1, 4))

                kpoint_deltas = self._clip_pad(kpoint_deltas, (height, width))
                kpoint_deltas = kpoint_deltas.transpose((0, 2, 3, 1)).reshape((-1, 10))

                scores = self._clip_pad(scores, (height, width))
                scores = scores.transpose((0, 2, 3, 1)).reshape((-1, 1))

                # print(anchors.shape, bbox_deltas.shape, A, K, file=sys.stderr)
                proposals = self._bbox_pred(anchors, bbox_deltas)
                proposals = clip_boxes(proposals, im_info[:2])  #将超出图像的坐标去除掉

                proposals_kp = kpoint_pred(anchors, kpoint_deltas)
                proposals_kp = clip_points(proposals_kp, im_info[:2])
                #取出score的top N
                scores_ravel = scores.ravel()
                order = scores_ravel.argsort()[::-1]
                if pre_nms_topN > 0:
                    order = order[:pre_nms_topN]
                proposals = proposals[order, :]
                proposals_kp = proposals_kp[order, :]
                scores = scores[order]

                proposals /= im_scale
                proposals_kp /= im_scale

                proposals_list.append(proposals)
                proposals_kp_list.append(proposals_kp)
                scores_list.append(scores)

        proposals = np.vstack(proposals_list)
        proposals_kp = np.vstack(proposals_kp_list)
        scores = np.vstack(scores_list)
        scores_ravel = scores.ravel()
        order = scores_ravel.argsort()[::-1]
        #if config.TEST.SCORE_THRESH>0.0:
        #  _count = np.sum(scores_ravel>config.TEST.SCORE_THRESH)
        #  order = order[:_count]
        #if pre_nms_topN > 0:
        #    order = order[:pre_nms_topN]
        proposals = proposals[order, :]
        proposals_kp = proposals_kp[order, :]
        scores = scores[order]

        det = np.hstack((proposals, scores, proposals_kp)).astype(np.float32)

        #if np.shape(det)[0] == 0:
        #    print("Something wrong with the input image(resolution is too low?), generate fake proposals for it.")
        #    proposals = np.array([[1.0, 1.0, 2.0, 2.0]]*post_nms_topN, dtype=np.float32)
        #    scores = np.array([[0.9]]*post_nms_topN, dtype=np.float32)
        #    det = np.array([[1.0, 1.0, 2.0, 2.0, 0.9]]*post_nms_topN, dtype=np.float32)


        if self.nms_threshold < 1.0:
            keep = self.nms(det)
            det = det[keep, :]
        if threshold > 0.0:
            keep = np.where(det[:, 4] >= threshold)[0]
            det = det[keep, :]
        return det