예제 #1
0
    def _loss_mask(self, proto_output, pred_mask_coef, gt_bbox_norm, gt_masks, positiveness,
                   max_id_for_anchors, max_masks_for_train):

        shape_proto = tf.shape(proto_output)
        num_batch = shape_proto[0]
        loss_mask = 0.
        total_pos = 0
        for idx in tf.range(num_batch):
            # extract randomly postive sample in pred_mask_coef, gt_cls, gt_offset according to positive_indices
            proto = proto_output[idx]
            mask_coef = pred_mask_coef[idx]
            mask_gt = gt_masks[idx]
            bbox_norm = gt_bbox_norm[idx]
            pos = positiveness[idx]
            max_id = max_id_for_anchors[idx]
            pos_indices = tf.squeeze(tf.where(pos == 1))
            # tf.print("num_pos", tf.shape(pos_indices))
            """
            if tf.size(pos_indices) == 0:
                tf.print("detect no positive")
                continue
            """
            # Todo decrease the number pf positive to be 100
            # [num_pos, k]
            pos_mask_coef = tf.gather(mask_coef, pos_indices)
            pos_max_id = tf.gather(max_id, pos_indices)

            if tf.size(pos_indices) == 1:
                # tf.print("detect only one dim")
                pos_mask_coef = tf.expand_dims(pos_mask_coef, axis=0)
                pos_max_id = tf.expand_dims(pos_max_id, axis=0)
            total_pos += tf.size(pos_indices)
            
            # proto = [80, 80, num_mask]
            # pos_mask_coef = [num_pos, num_mask]
            # pred_mask = proto x pos_mask_coef = [80, 80, num_pos]
            # pred_mask transpose = [num_pos, 80, 80]
            pred_mask = tf.linalg.matmul(proto, pos_mask_coef, transpose_a=False, transpose_b=True)
            pred_mask = tf.transpose(pred_mask, perm=(2, 0, 1))

            # calculating loss for each mask coef correspond to each postitive anchor
            # pos_max_id = [num_pos]
            gt = tf.gather(mask_gt, pos_max_id)            # [num_pos, 80, 80]
            bbox = tf.gather(bbox_norm, pos_max_id)        # [num_pos, 4]
            bbox_center = utils.map_to_center_form(bbox)   # [num_pos, 4]
            area = bbox_center[:, -1] * bbox_center[:, -2]

            # crop the pred (not real crop, zero out the area outside the gt box)
            s = tf.nn.sigmoid_cross_entropy_with_logits(gt, pred_mask)  # [num_pos, 80, 80]
            s = utils.crop(s, bbox, origin_w=80, origin_h=80)           # [num_pos, 80, 80]
            loss = tf.reduce_sum(s, axis=[1, 2]) / area                 # [num_pos]
            loss_mask += tf.reduce_sum(loss)

        loss_mask /= tf.cast(total_pos, tf.float32)
        return loss_mask
예제 #2
0
    def _loss_mask(self, protonet_output, pred_mask_coef, gt_bbox_norm,
                   gt_masks, positiveness, max_id_for_anchors,
                   max_masks_for_train):
        shape_proto = tf.shape(protonet_output)
        batch_size = shape_proto[0]
        loss_mask = 0.
        total_pos = 0
        for idx in tf.range(batch_size):
            # extract randomly postive sample in pred_mask_coef, gt_cls, gt_offset according to positive_indices
            proto = protonet_output[idx]
            mask_coef = pred_mask_coef[idx]
            mask_gt = gt_masks[idx]
            bbox_norm = gt_bbox_norm[idx]
            pos = positiveness[idx]
            max_id = max_id_for_anchors[idx]

            pos_indices = tf.squeeze(tf.where(pos == 1))
            # tf.print("num_pos", tf.shape(pos_indices))

            # TODO: Limit number of positive to be less than max_masks_for_train
            pos_mask_coef = tf.gather(mask_coef, pos_indices)
            pos_max_id = tf.gather(max_id, pos_indices)
            if tf.size(pos_indices) == 1:
                # tf.print("detect only one dim")
                pos_mask_coef = tf.expand_dims(pos_mask_coef, axis=0)
                pos_max_id = tf.expand_dims(pos_max_id, axis=0)
            total_pos += tf.size(pos_indices)
            pred_mask = tf.linalg.matmul(proto,
                                         pos_mask_coef,
                                         transpose_a=False,
                                         transpose_b=True)
            pred_mask = tf.transpose(pred_mask, perm=(2, 0, 1))

            # calculating loss for each mask coef correspond to each postitive anchor
            gt = tf.gather(mask_gt, pos_max_id)
            bbox = tf.gather(bbox_norm, pos_max_id)
            bbox_center = utils.map_to_center_form(bbox)
            area = bbox_center[:, -1] * bbox_center[:, -2]

            # crop the pred (not real crop, zero out the area outside the gt box)
            s = tf.nn.sigmoid_cross_entropy_with_logits(gt, pred_mask)
            s = utils.crop(s, bbox)
            loss = tf.reduce_sum(s, axis=[1, 2]) / area
            loss_mask += tf.reduce_sum(loss)

        loss_mask /= tf.cast(total_pos, tf.float32)
        return loss_mask
예제 #3
0
    def _loss_mask(self, proto_output, pred_mask_coef, gt_bbox_norm, gt_masks,
                   positiveness, max_id_for_anchors, max_masks_for_train):

        shape_proto = tf.shape(proto_output)
        num_batch = shape_proto[0]
        proto_h = shape_proto[1]
        proto_w = shape_proto[2]
        loss_mask = 0.
        total_pos = 0

        for idx in tf.range(num_batch):
            # extract randomly postive sample in prejd_mask_coef, gt_cls, gt_offset according to positive_indices
            proto = proto_output[idx]
            mask_coef = pred_mask_coef[idx]
            mask_gt = gt_masks[idx]
            bbox_norm = gt_bbox_norm[idx]  # [100, 4] -> [num_obj, 4]
            pos = positiveness[idx]
            max_id = max_id_for_anchors[idx]

            pos_indices = tf.squeeze(tf.where(pos == 1))

            # If exceeds the number of masks for training, select a random subset
            old_num_pos = tf.size(pos_indices)
            # print("pos indices", pos_indices.shape)
            if old_num_pos > max_masks_for_train:
                perm = tf.random.shuffle(pos_indices)
                pos_indices = perm[:max_masks_for_train]

            pos_mask_coef = tf.gather(mask_coef, pos_indices)
            pos_max_id = tf.gather(max_id, pos_indices)

            # if only 1 positive or no positive
            if tf.size(pos_indices) == 1:
                pos_mask_coef = tf.expand_dims(pos_mask_coef, axis=0)
                pos_max_id = tf.expand_dims(pos_max_id, axis=0)
            elif tf.size(pos_indices) == 0:
                continue
            else:
                ...

            # [num_pos, k]
            gt = tf.gather(mask_gt, pos_max_id)
            bbox = tf.gather(bbox_norm, pos_max_id)
            # print(bbox[:5])
            num_pos = tf.size(pos_indices)
            # print('gt_me', gt.shape)
            total_pos += num_pos

            # [138, 138, num_pos]
            pred_mask = tf.linalg.matmul(proto,
                                         pos_mask_coef,
                                         transpose_a=False,
                                         transpose_b=True)
            pred_mask = tf.transpose(pred_mask, perm=(2, 0, 1))
            s = tf.nn.sigmoid_cross_entropy_with_logits(gt, pred_mask)
            s = utils.crop(s, bbox)

            # calculating loss for each mask coef correspond to each postitive anchor
            bbox_center = utils.map_to_center_form(tf.cast(bbox, tf.float32))
            area = bbox_center[:, -1] * bbox_center[:, -2]
            mask_loss = tf.reduce_sum(s, axis=[1, 2]) / area

            if old_num_pos > num_pos:
                mask_loss = mask_loss * tf.cast(
                    (old_num_pos / num_pos), mask_loss.dtype)
            loss_mask += tf.reduce_sum(mask_loss)

        return loss_mask / tf.cast(total_pos, loss_mask.dtype)