使用旋转矩阵和常规 ImageNet 标准差计算灰度 ImageNet 像素值的标准差

问题描述 投票:0回答:2

我想训练一些模型来处理灰度图像,例如对于显微镜应用很有用(来源)。因此,我想使用 pytorch 灰度转换(torchvision.transforms.Grayscale)在灰度 imagenet 上训练我的模型,将 RGB imagenet 转换为灰度 imagenet。 pytorch 内部将颜色空间从 RGB 旋转到 YPbPr,如下所示:

enter image description here

Y'为灰度通道,因此变换后可以忽略Pb和Pr。其实pytorch甚至只是计算

grayscale = (0.2989 * r + 0.587 * g + 0.114 * b)

为了标准化图像数据,我需要知道grayscale-imagenet的平均像素值以及标准差。这些可以计算吗?

我成功地使用

计算了平均像素强度
meanGrayscale = 0.2989 * r.mean() + 0.587 * g.mean() + 0.114 * b.mean()

变换图像然后计算灰度平均值,得到的结果与先计算 RGB 平均值然后将其转换为灰度平均值相同。

但是,我现在对计算方差或标准差一无所知。有人有任何想法,或者知道一些关于这个主题的好文献吗?这可能吗?

我找到了一本出版物《龚建新 - 澄清标准差椭圆》……他在二维中做到了这一点(据我所知)。我只是还不知道如何在 3D 中做到这一点。

image-processing color-scheme standard-deviation rotational-matrices
2个回答
4
投票

好吧,我无法按计划计算标准差,但使用下面的代码进行了计算。灰度 imagenet 的训练数据集平均值和标准差是(根据需要舍入):

平均值:0.44531356896770125

标准偏差:0.2692461874154524

import multiprocessing
import os

def calcSTD(d):
    meanValue = 0.44531356896770125
    squaredError = 0
    numberOfPixels = 0
    for f in os.listdir("/home/imagenet/ILSVRC/Data/CLS-LOC/train/"+str(d)+"/"): 
        if f.endswith(".JPEG"):
            
            image = imread("/home/imagenet/ILSVRC/Data/CLS-LOC/train/"+str(d)+"/"+str(f))
                
            ###Transform to gray if not already gray anyways  
            if  np.array(image).ndim == 3:
                matrix = np.array(image)
                blue = matrix[:,:,0]/255
                green = matrix[:,:,1]/255
                red = matrix[:,:,2]/255
                gray = (0.2989 * red + 0.587 * green + 0.114 * blue)
            else:
                gray = np.array(image)/255
            ###----------------------------------------------------       
                    
            for line in gray:
                for pixel in line:
                    squaredError += (pixel-meanValue)**2
                    numberOfPixels += 1
    
    return (squaredError, numberOfPixels)

a_pool = multiprocessing.Pool()
folders = []
[folders.append(f.name) for f in os.scandir("/home/imagenet/ILSVRC/Data/CLS-LOC/train") if f.is_dir()]
resultStD = a_pool.map(calcSTD, folders)

StD = (sum([intensity[0] for intensity in resultStD])/sum([pixels[1] for pixels in resultStD]))**0.5
print(StD)

过程中出现了一些类似这样的错误:

/opt/conda/lib/python3.7/site-packages/PIL/TiffImagePlugin.py:771: 用户警告:EXIF 数据可能已损坏。 预计读取 8 个字节 但只得到 4。跳过标签 41486“可能损坏 EXIF 数据。”

跳过了 2019 版 ImageNet 中的相应图像。


0
投票

要计算灰度 ImageNet 像素值的标准差,您确实可以使用您提到的转换公式。使用以下公式执行从 RGB 到灰度的转换:

{grayscale} = 0.2989 X R + 0.587 X G + 0.114 X B

您使用以下方法成功计算了平均灰度像素值:

meanGrayscale = 0.2989 * r.mean() + 0.587 * g.mean() + 0.114 * b.mean()

现在,为了计算标准差,我们可以使用方差的属性。标准差是方差的平方根,计算公式如下:

  1. 计算方差: 应用转换系数,可以从 RGB 通道的方差导出灰度值的方差。给定灰度公式,方差由下式给出:

    在此输入图片描述

    其中R、G、B符号是各自RGB通道的方差。

  2. 计算标准差: 最后,灰度图像的标准差可以计算为:

    在此输入图片描述

以下是如何使用 PyTorch 在 Python 中实现此功能:

import torch

# Assuming r, g, b are your RGB channel tensors
r = torch.randn(1000)  # Example tensor for red channel
g = torch.randn(1000)  # Example tensor for green channel
b = torch.randn(1000)  # Example tensor for blue channel

# Calculate means
mean_r = r.mean()
mean_g = g.mean()
mean_b = b.mean()

# Calculate variances
var_r = r.var(unbiased=False)  # Population variance
var_g = g.var(unbiased=False)
var_b = b.var(unbiased=False)

# Calculate grayscale mean
meanGrayscale = 0.2989 * mean_r + 0.587 * mean_g + 0.114 * mean_b

# Calculate grayscale variance
var_gray = (0.2989**2 * var_r) + (0.587**2 * var_g) + (0.114**2 * var_b)

# Calculate grayscale standard deviation
std_gray = var_gray.sqrt()

print(f"Mean Grayscale Value: {meanGrayscale.item()}")
print(f"Standard Deviation of Grayscale Values: {std_gray.item()}")

这将为您提供灰度 ImageNet 像素值的平均值和标准差,您可以将其用于模型中的标准化。

© www.soinside.com 2019 - 2024. All rights reserved.