Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/image/5.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Image &引用;标准;RGB到灰度转换_Image_Algorithm_Jpeg_File Conversion_Pgm - Fatal编程技术网

Image &引用;标准;RGB到灰度转换

Image &引用;标准;RGB到灰度转换,image,algorithm,jpeg,file-conversion,pgm,Image,Algorithm,Jpeg,File Conversion,Pgm,我正在尝试编写一个转换器算法,它获取JPEG图像并返回其PGM(便携式灰度图)版本。 问题是,我无法理解“官方”JPG->PGM转换器是如何从经典RGB格式开始为最终像素分配什么值的 开始时,我使用了这个公式(OpenCV的CV_RGB2GRAY转换也使用了这个公式): 0.30*R+0.59*G+0.11*B=val 我编写了一个简单的代码来测试我的结果:它采用彩色图像及其PGM版本(已使用GIMP转换)。然后使用前面的公式转换彩色图像。目标是使灰度图像像素到像素等于PGM输入 此时,它不会返

我正在尝试编写一个转换器算法,它获取JPEG图像并返回其PGM(便携式灰度图)版本。 问题是,我无法理解“官方”JPG->PGM转换器是如何从经典RGB格式开始为最终像素分配什么值的

开始时,我使用了这个公式(OpenCV的CV_RGB2GRAY转换也使用了这个公式):

0.30*R+0.59*G+0.11*B=val

我编写了一个简单的代码来测试我的结果:它采用彩色图像及其PGM版本(已使用GIMP转换)。然后使用前面的公式转换彩色图像。目标是使灰度图像像素到像素等于PGM输入


此时,它不会返回相同的值。你能帮我吗

理论上,只需几个像素(本例中为3个像素),就可以确定他们的算法在做什么。 只需选择三个像素(p1、p2、p3)、它们的RGB值和PGM灰度值,即可:

红色常量*p1.redValue+绿色常量*p1.greenValue+蓝色常量*p1.blueValue=p1.grayValue

RedConstant*p2.redValue+GreenConstant*p2.greenValue+BlueConstant*p2.blueValue=p2.grayValue

RedConstant*p3.redValue+GreenConstant*p3.greenValue+BlueConstant*p3.blueValue=p3.grayValue

然后解决这个问题(查找“方程求解器”或其他东西),看看他们使用的常数是什么

问题是,我无法理解“官方”JPG->PGM转换器是如何从经典RGB格式开始为最终像素分配什么值的

“官方”工具正在使用的转换中可能存在伽马调整。
也就是说,它不仅仅是线性转换。

有关详细信息,请参阅此Wikipedia部分:

我相信您希望使用
Csrgb

的公式,尝试一下,看看它是否符合您期望的结果

基本上,您将这样做:

  • 采用
    R,G,B
    颜色(每个在
    [0,1]
    范围内)
    • 如果它们在
      0..255
      范围内,只需除以
      255.0
  • 计算
    Clinear=0.2126 R+0.7152 G+0.0722 B
    • 这可能是您以前应用的线性变换
  • 根据
    Clinear
    • 这是您丢失的非线性伽马校正片
    • 退房
    • Csrgb=12.92 Clinear
      Clinear 0.0031308

  • 在OPENCV PYTHON中将RGB图像转换为灰度的简单算法

    我使用了注释,所以代码是不言自明的。但它工作得很快

    import cv2
    import numpy as np
    img1 = cv2.imread('opencvlogo.png')
    row,col,ch = img1.shape
    g = [ ]  #the list in which we will stuff single grayscale pixel value inplace of 3 RBG values
    #this function converts each RGB pixel value into single Grayscale pixel value and appends that value to list 'g'
    def rgb2gray(Img):
        global g
        row,col,CHANNEL = Img.shape
        for i in range(row) :
            for j in range(col):
            a =      (   Img[i,j,0]*0.07  +  Img[i,j,1]*0.72 +    Img[i,j,2] *0.21   ) #the algorithm i used id , G =  B*0.07 + G*0.72 + R* 0.21
                                                                                       #I found it online
            g.append(a)
    rgb2gray(img1)  #convert the img1 into grayscale
    gr = np.array(g)  #convert the list 'g' containing grayscale pixel values into numpy array
    cv2.imwrite("test1.png" , gr.reshape(row,col)) #save the image file as test1.jpg
    
    所以我用了这个图像文件

    我的程序生成了以下灰度文件


    哈罗德关于“Y平面”的观点:标准彩色JPEG使用颜色空间编码,其中Y是亮度分量(即亮度),Cb和Cr是蓝差和红差色度分量。因此,将彩色JPEG转换为灰度JPEG的一种方法是简单地删除Cb和Cr组件


    有一个名为
    jpegtran
    的实用程序,它可以使用
    -grayscale
    选项无损地执行此操作。(为了避免这种情况,无损部分实际上只在您希望最终使用JPEG而不是PGM时才起作用。)无论如何,这可能是进行这种转换的最快方法,因为它甚至不会将图像解码为像素,更不用说对每个像素进行数学运算了。

    将默认RGB颜色模型中的单个输入像素转换为单个灰色像素

    /* Convertation function 
     * @param x    the horizontal pixel coordinate
     * @param y    the vertical pixel coordinate
     * @param rgb  the integer pixel representation in the default RGB color model
     * @return a gray pixel in the default RGB color model.*/
    
        public int filterRGB(int x, int y, int rgb) {
        // Find the average of red, green, and blue.
        float avg = (((rgb >> 16) & 0xff) / 255f +
                     ((rgb >>  8) & 0xff) / 255f +
                      (rgb        & 0xff) / 255f) / 3;
        // Pull out the alpha channel.
        float alpha = (((rgb >> 24) & 0xff) / 255f);
    
        // Calculate the average.
        // Formula: Math.min(1.0f, (1f - avg) / (100.0f / 35.0f) + avg);
        // The following formula uses less operations and hence is faster.
        avg = Math.min(1.0f, 0.35f + 0.65f * avg);
        // Convert back into RGB.
       return (int) (alpha * 255f) << 24 |
              (int) (avg   * 255f) << 16 |
              (int) (avg   * 255f) << 8  |
              (int) (avg   * 255f);
    }
    
    /*转换功能
    *@param x水平像素坐标
    *@param y垂直像素坐标
    *@param rgb默认rgb颜色模型中的整数像素表示
    *@返回默认RGB颜色模型中的灰色像素*/
    公共整型过滤器rgb(整型x、整型y、整型rgb){
    //找到红色、绿色和蓝色的平均值。
    浮点平均值=((rgb>>16)和0xff)/255f+
    ((rgb>>8)和0xff)/255f+
    (rgb&0xff)/255f)/3;
    //拉出alpha通道。
    浮点alpha=((rgb>>24)和0xff)/255f);
    //计算平均值。
    //公式:数学最小值(1.0f,(1f-平均值)/(100.0f/35.0f)+平均值);
    //以下公式使用更少的运算,因此速度更快。
    平均值=数学最小值(1.0华氏度,0.35华氏度+0.65华氏度*平均值);
    //转换回RGB。
    
    return(int)(alpha*255f)平均法是最简单的方法。你只需要取三种颜色的平均值。因为它是RGB图像,所以这意味着你必须将r与g和b相加,然后将其除以3,得到你想要的灰度图像

    它是这样做的

    Grayscale = (R + G + B / 3)
    

    如果你有一张彩色图像,如上图所示,你想用平均法将其转换为灰度。

    谢谢,但不行。我输入了3个像素值,并解出了一个三方程组。它得到了三个常数,这三个常数适用于这些方程,而不适用于第四个像素。1)你确定选择了相同的像素吗对于RGB和灰度值?2)从这篇文章中:我看到它们是几种不同的RGB到PGM算法。尝试所有的RGB到PGM算法,并尝试找出使用哪一种算法。祝你好运!如果我告诉你我没有找到任何有效的方法怎么办?嗯,GIMP可能使用了他们自己的奇怪算法,尝试精确地重新创建他们的转换器的真正目的是什么?PGM转换的过程是一个较长算法的一个子部分。经过一些测试,我发现如果我使用“GIMP”PGM图像作为输入,而不是使用所有这些方法创建的更简单的版本,这种算法的结果会更好。因此我认为真正的PGM格式描述像素值的方式似乎更“易于管理”根据我的算法,我还