ValueError('need at least one array to stack') ValueError: need at least one array to stac

使用mmdetection做实例分割过程中踩的一个大坑。

ValueError('need at least one array to stack') ValueError: need at least one array to stac_第1张图片

 经过反复调试后,终于发现是数据集的问题。在实例分割中,分割标签的键'iscrowd'为1的时候,标签会被抛弃,全为1的时候,就会发生以上错误。出错原因代码如下

ValueError('need at least one array to stack') ValueError: need at least one array to stac_第2张图片

 iscrowd表示一个以上物体连在一个,作为一个整体,如人群,所以做实例分割时候会被过滤掉。而在coco数据集中。iscrowd的取值取决于标签segmentation的格式,格式为RLE的时候,iscrowd为1,格式为polygon的时候,iscrowd为0。所以当你自己的数据标签的segmentation全为RLE格式的时候,你的所有标签都会被抛弃,错误在所难免。于是就要将RLE格式转为polygon格式。代码如下,

代码参考:

https://github.com/facebookresearch/Detectron/issues/100

https://tianchi.aliyun.com/competition/entrance/231787/information

RLE转polygon

import numpy as np
import json
from tqdm import tqdm
import random
import os
import cv2
import matplotlib.pyplot as plt
import pycocotools.mask as maskUtils

def annToRLE(ann, i_w, i_h):
    h, w = i_h, i_w
    segm = ann['segmentation']
    if type(segm) == list:
        # polygon -- a single object might consist of multiple parts
        # we merge all parts into one mask rle code
        rles = maskUtils.frPyObjects(segm, h, w)
        rle = maskUtils.merge(rles)
    elif type(segm['counts']) == list:
        # uncompressed RLE
        rle = maskUtils.frPyObjects(segm, h, w)
    else:
        # rle
        rle = ann['segmentation']
    return rle


rle = annToRLE(ann_fu, ann_fu['segmentation']['size'][0], ann_fu['segmentation']['size'][1])
mask = maskUtils.decode(rle)
contours, _ = cv2.findContours(mask, cv2.RETR_TREE, cv2.CHAIN_APPROX_SIMPLE)
# after opencv 3.2
# _, contours, hierarchy = cv2.findContours((mask).astype(np.uint8), cv2.RETR_TREE,
#                                                    cv2.CHAIN_APPROX_SIMPLE)
segmentation = []
for contour in contours:
    contour = contour.flatten().tolist()
    if len(contour) > 4:
        segmentation.append(contour)
ann_coco['segmentation'] = segmentation

 

 值得注意的是,contours, _ = cv2.findContours(mask, cv2.RETR_TREE, cv2.CHAIN_APPROX_SIMPLE)这句可能报错,原因是版本问题。opencv版本高于3.2时,有三个输出,要用  _, contours, _ , 否则,使用 contours, _  。

你可能感兴趣的:(mmdetection,踩坑日记,pytorch,深度学习)