语义分割中label伪彩图或者调色板转换(palette) 基于VOC数据集

voc语义分割数据集

介绍网上有很多,可以自己查一查,比如:https://blog.csdn.net/qq_41997920/article/details/104914129
常见的图片格式一般为rgb彩色三通道图或者单通道灰度图,但作为语义分割的label图(以voc数据集为例),其png图片实际格式是单通道的彩色图,这里叫伪彩图(或者也叫索引图吧)。由于将图片分割后是把像素点分类,不同类的分割结果用不同颜色表示(此时的类别远远小于平时彩色图里256256256的组合类别),因此我们只需要定义一个类似于有序字典的东西来表示颜色即可(大大减少储存的数据量),正好伪彩图就派上了用场。

伪彩图

伪彩图在我理解来说就是字典只不过并不是直接的那种字典关系,实际做法其实是先定义颜色结构,通过颜色的索引代表颜色
举例:比如我们这里需要三种颜色,那就定义三种颜色[[255, 0, 0], [0, 255, 0],[0, 0, 255]]的结构储存起来,此时我们的伪彩色图片(只会出现上面三类颜色)就不需要用三通道的0-255矩阵去表示了,当像素点的颜色为[255, 0, 0]时,只需要用0表示即可,这里的0就是颜色结构里的第一个颜色。同样地,1,2就分别表示另外两个颜色。
这里可以参考一下一些讲解伪彩图或者调色板的其他博客:
调色板

图片转化为VOC数据集label的调色板模式

这里其实我参考的是这位大佬的代码:
https://blog.csdn.net/weixin_39539684/article/details/111665128?utm_medium=distribute.pc_relevant.none-task-blog-baidujs_title-1&spm=1001.2101.3001.4242

这位大佬不仅讲解了VOC语义分割数据集的label,还使用了两个库分别转换伪彩图。
我使用他的PIL那一版,稍微加了注释,简单改成了一个方法,有需要的可以按自己需要修改使用。

import glob
from PIL import Image
import cv2
import matplotlib.image as mi
import matplotlib.pyplot as plt
import numpy as np
import png # https://pypng.readthedocs.io/en/latest/


# 使用PIL库生成调色板格式的图
def Convert_Palette(img_png):
    voc_label_path = r'F:\Python-file\data\PASCAL_VOC\VOCdevkit\VOC2012\SegmentationClass\2007_000032.png'
    png_data = png.Reader(voc_label_path)
    # print(png_data.read()) 这里可以获取该png图片的信息(tuple格式储存的),如果是调色板图片,还可以获取调色板
    voc_palette = png_data.read()[3]['palette'] # 得到voc的label的调色板(list形式储存的)
    palette = np.array(voc_palette) # 256*3
    palette = palette.reshape(256, 1, 3).astype(np.uint8) # 256*1*3 把int32改成uint8(opencv中储存图像的数据格式 0 - 256)

    out_img = Image.open(img_png)
    out_img.putpalette(palette) # 就是以刚刚得到的调色板将图片转换为调色板模式的伪彩图
    out_img.save(r'F:\Python-file\data\surface detection\Magnetic-tile-defect-datasets.-master\label\out.png')

可以调用一下上面代码并用img.mode看一下原图的mode和convert之后的图的mode是否变成了’P’,这里的mode P是PIL库表示图片为调色板格式的标志。
PIL默认有一个调色板好像就是VOC使用的调色板,有兴趣的可以自己试试。
以上为我个人理解,如有不对的地方请指正,希望给大家带来帮助

你可能感兴趣的:(毕业论文记录,语义分割入门日志,深度学习,神经网络,自动驾驶)