本文主要是介绍Debug日记:为什么神经网络测试精度远低于验证精度??都是模式“P”惹的祸!!,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!
事情背景
最近在做一个图像分割的项目,数据集是自己制作的VOC格式的分割数据集,在之前的博客中,我发现了VOC数据集的ground turth是8位的彩色图像。
后来查了很多资料,暂时只找到PIL.Image有的调色板模式“P”是8位的彩色图像。于是将训练集、验证集都转换为模式“P”之后就开始训练了。
经过了艰苦的调参,模型终于不会过拟合了,但是在测试的时候却发现,测试的精度接近于瞎猜(二分类)。
起初以为是模型的问题或者验证集的标签泄露。但是冷静分析一下,肯定不是过拟合,原因有二:
- 如果验证集的标签泄露,那么不可能需要那么小心地设计学习率,它才不会过拟合,而是随便设计学习率都可以完美地拟合
- 就算它泄露了,就算模型泛化能力极差,也不至于完全是瞎猜的状态。
在仔细检查了代码之后,感觉可能是因为模式“P”的原因!经过了实验,终于定位了问题,就是模式"P"惹的祸!!
>>> import numpy as np
>>> test = np.zeros((2,2,3),dtype="uint8")
>>> test[0][1]=[1,1,1]
>>> test
array([[[0, 0, 0],[1, 1, 1]],[[0, 0, 0],[0, 0, 0]]], dtype=uint8)
>>> import numpy as np
>>> test = np.ones((2,2,3),dtype="uint8")
>>> test[0][1]=[0,0,0]
>>> test
array([[[1, 1, 1],[0, 0, 0]],[[1, 1, 1],[1, 1, 1]]], dtype=uint8)
>>> from PIL import Image
>>> img1 = Image.fromarray(test)
>>> L1 = img1.convert("L")
>>> P1 = L1.convert("P")
>>> img2 = Image.fromarray(test)
>>> P2 = img2.convert("P")
>>> P1 == P2
False
>>> np.array(P1.convert("RGB"))
array([[[1, 1, 1],[0, 0, 0]],[[1, 1, 1],[1, 1, 1]]], dtype=uint8)
>>> np.array(P2.convert("RGB"))
array([[[0, 0, 0],[0, 0, 0]],[[0, 0, 0],[0, 0, 0]]], dtype=uint8)
see?一张RGB的图像,用PIL.Image.Open.convert直接转化为模式“P”的结果,和先转化为模式“L”再转化为模式“P”是不一样的!!!
我在生成训练集和验证集的时候,将RGB的图像转化为模式“L”,再转化为模式“P”。而在生成验证集的时候,直接将RGB的图像直接转化为了模式“P”。就是这一个不起眼的失误浪费了几天的时间!
至于为什么二值的RGB直接转模式P会得到全0的矩阵,小弟还没想明白,希望评论区有高人解答!!
这篇关于Debug日记:为什么神经网络测试精度远低于验证精度??都是模式“P”惹的祸!!的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!