本人刚接触这方面不久,在网上搜索了很多文章,发现很多文章都存在一些弊端,自己做了一些总结,方法比较基础,但亲测有效。
首先,我们得有一些原始图片,然后通过labelme标注后得到json文件(labelme使用大家可以去搜一下),接下来我们需要做的是将json文件转换为可用于训练的标签集。
网上很多说python中自带了一个脚本json_to_dataset.py可以转换(路径在python安装路径下,比如我的是在D:\python3.6.7\Lib\site-packages\labelme\cli中),调用方法是在cmd下输入: labelme_json_to_dataset <文件路径>.json,就可以得到标签图片(保存路径就是json文件目录下),但有一个问题就是,一次性只能转换一张标签,这多麻烦啊。于是,很多人写了脚本,可以批量化转换,但就我目前看到批量转换脚本,大多存在着一个致命的问题,就是对于不同图片,他的类别标注是对应不上的(这些脚本只是负责把图送到json_to_dataset.py,并没有对标签进行其他处理),看下图:
在这里插入图片描述 在这里插入图片描述
从上面两张图片可以看出,两种完全不是同一类别的东西都被赋予相同的颜色(也即相同标签),这肯定不是我们想要的。
然后就想尝试了一个比较官方的方法: 先将json文件转换为voc格式的文件 (为什么要这样做呢,因为voc格式算是比较官方的格式,针对其的转换程序也是正规的,解决了批量转换和不同类别时被赋予不同的像素的问题),然后就在github上找打了一个voc的转换脚本,链接在这里: https://github.com/wkentaro/labelme/tree/master/examples/semantic_segmentation ,里面有教程教你怎么调用,这里就直接写下吧,cmd下输入:
python ./labelme2voc.py(尽量写绝对路径) 图片和json文件存放的路径(放在一起) 保存路径 --labels labels.txt路径(中间都是空格隔开)
这里需要注意的是,你需要将你自己的标签类别制作成一个txt文本(也就是上面调用命令中的labels.txt),你可以仿照上面那个链接中的labels.txt做,这个程序会根据你的类别去转换,然后你就会得到四个文件夹,其中有用的只有两个JPEGImages(原图像),SegmentationClassPNG(voc格式的标签图像),转换后的标签如下图所示:
在这里插入图片描述 在这里插入图片描述
可以看到,两种不同的东西被赋予了不同的标签,但是这种图片是索引图(索引图是为了增强灰度图的差异性,其实他也是单通道的,只不过每一个灰度都对应着一种颜色),如果你的模型是要求索引图作为标签,那么到这里就已经完成了;如果你的模型是要求灰度图作为标签,那么还得进行第二步转换(错把索引图当做灰度图作为标签,可能出现label out of boundary的错误提示),即 将voc格式的索引图转换为可用于训练的灰度图 (看上去是全黑的)。这里有两种方法:
1.先读取索引图中各种类别的像素值,然后一一改过来,比如上面球像素值是125,然后遍历就把所有图片中的125的像素值都改为1(表示第一个类别),而红色的是225,就把所有图片中的225都改为2,然后再保存为灰度图格式就可以了。这种方法对于类别较多的就比较麻烦,而且遍历每一个像素值耗时很大。
2.第二种是我在网上找到的转换脚本,很快很好用

"" "Removes the color map from segmentation annotations . Removes the color map from the ground truth segmentation annotations and save the results to output_dir . #源程序链接:https : / / github . com / tensorflow / models / tree / master / research / deeplab / datasets #该程序用于将voc格式的索引图片转换为可用于语义分割的灰度图片,因为TensorFlow版本的缘故,在原程序上做了少许改动 #tf.__version__==1.12 import glob import os . path import numpy as np from PIL import Image import tensorflow as tf #FLAGS = tf.compat.v1.flags.FLAGS FLAGS = tf . flags . FLAGS tf . flags . DEFINE_string ( 'original_gt_folder' , #读取voc格式的png图片路径 'F:\Dataset_segmentaion\data_dataset_voc\SegmentationClassPNG' , # default 'Original ground truth annotations.' ) #help tf . flags . DEFINE_string ( 'segmentation_format' , 'png' , 'Segmentation format.' ) tf . flags . DEFINE_string ( 'output_dir' , #保存路径 'F:\Dataset_segmentaion\data_dataset_voc\labels' , 'folder to save modified ground truth annotations.' ) def _remove_colormap ( filename ) : "" "Removes the color map from the annotation . Args : filename : Ground truth annotation filename . Returns : Annotation without color map . return np . array ( Image . open ( filename ) ) def _save_annotation ( annotation , filename ) : "" "Saves the annotation as png file . Args : annotation : Segmentation annotation . filename : Output filename . pil_image = Image . fromarray ( annotation . astype ( dtype = np . uint8 ) ) with tf . io . gfile . GFile ( filename , mode = 'w' ) as f : #with open(filename, mode='w') as f: print ( f ) pil_image . save ( f , 'PNG' ) pil_image . save ( filename ) def main ( unused_argv ) : # Create the output directory if not exists. if not os . path . exists ( FLAGS . output_dir ) : os . makedirs ( FLAGS . output_dir ) # if not tf.io.gfile.isdir(FLAGS.output_dir): #tf.io.gfile.makedirs(FLAGS.output_dir) annotations = glob . glob ( os . path . join ( FLAGS . original_gt_folder , '*.' + FLAGS . segmentation_format ) ) for annotation in annotations : raw_annotation = _remove_colormap ( annotation ) filename = os . path . basename ( annotation ) [ : - 4 ] _save_annotation ( raw_annotation , os . path . join ( FLAGS . output_dir , filename + '.' + FLAGS . segmentation_format ) ) if __name__ == '__main__' : #tf.compat.v1.app.run() tf . app . run ( )

只需要将上面存放voc格式的png图像路径以及保存路径改成你自己的路径即可,转换后的图片是这样的:
在这里插入图片描述 在这里插入图片描述
你没有看错,就是全黑的,但只是看上去,除了背景像素值为零,其他的像素值不是零(可以调用np.unique(image)看看),比如你有21个类别,那么,对应的像素就是0-21,但看上去就是一团黑,不好分辨,因此才有了上面的索引图。到这里,标签图片就只做完成了,希望对大家有帮助。

本人刚接触这方面不久,课题是关于语义分割的内容,在网上搜索了很多文章,发现很多文章都存在一些弊端,自己做了一些总结,方法比较基础,但亲测有效。首先,我们得有一些原始图片,然后通过labelme标注后得到json文件(labelme使用大家可以去搜一下),接下来我们需要做的是将json文件转换为可用于训练的标签集。网上很多说python中自带了一个脚本json_to_dataset.py可以转换...
模型在FloodNet数据集上进行了训练,mIOU在0.83左右,可训练自己的数据集 建议在训练网络的时候将输入的训练集其切分为384x384的小图片后,再来进行训练 模型采用标准的UNet,可以采用如下方式训练你自己的模型 数据集地址可以在train.py中修改为你自己的文件夹 python train.py -- --epochs 20 --batch-size 16 --learning-rate 2e-4 --scale 1 --validation 0.1 --classes 10 --amp 其中--amp为半精度训练 --scale是训练的时候对图片进行缩放,已经裁剪为384x384后就不需要再裁剪了
语义分割 动手实践 - labelme标注和 标签 生成 最近接触到 语义分割 任务,借助deeplabv3+和BiSeNet v2对分割任务有了初步的了解,为自己记录下整个流程 1、 语义分割 数据标注 标注工具:由于语义/实例分割任务多是多边形(polygons)轮廓标注,在此选用labelme标注工具。 labelme安装,有需要可以创建虚拟环境,有 python 和pyqt5即可: 创建labelme虚拟环境 conda create -n labelme python =3.8 激活虚拟环境 conda activa
如果没有安装anaconda3,可以跟着 anaconda安装配置教程 安装一下, 深度学习 必备工具。 进入anaconda中的 python 环境,然后输入pip install labelme,回车进行安装。 1、在 python 环境中输入labelme,回车就会打开下图所示的标注窗口。 2、点击左侧create polygons,开始框区域,鼠标点击就会放置一个点,然后拉线再放下一个点,这样环绕框....