3

我正在尝试运行一个简单的 Java 程序,该程序尝试执行以下操作:从给定图像中提取像素数据。然后使用此数据创建相同类型的新图像。问题是当我读取这个创建的图像的像素数据时,像素值与我写入的像素值不同。这种情况不仅发生在 .jpg 图像上,也发生在某些 .png 图像上(因此它甚至不限于图像类型)。这是我的代码:

package com.alex;

import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;

import javax.imageio.ImageIO;

public class Test {

    public static void main(String[] args) {
        try{
            // Read source image
            BufferedImage img = ImageIO.read(new File("D:/field.png")); 


            int width = img.getWidth();
            int height = img.getHeight();
            int[] imagePixels = new int[width*height];
            img.getRGB(0, 0, width, height, imagePixels, 0, width);

            // Create copy image
            BufferedImage destImg = new BufferedImage(img.getWidth(), img.getHeight(), img.getType());
            destImg.setRGB(0, 0, img.getWidth(), img.getHeight(), imagePixels, 0, img.getWidth());
            File out = new File("D:/test.png");
            ImageIO.write(destImg, "png", out);

            // Extract copy image pixels
            BufferedImage copy = ImageIO.read(new File("D:/test.png"));
            int width1 = copy.getWidth();
            int height1 = copy.getHeight();
            int[] extractedPixels = new int[width1*height1];
            copy.getRGB(0, 0, width1, height1, extractedPixels, 0, width1);

            System.out.println("The 2 dimensions are " + imagePixels.length + " " + extractedPixels.length );

            // Compare the piels from the 2 images
            int k=0;
            for(int i=0; i<imagePixels.length; i++) {
                if(imagePixels[i] != extractedPixels[i]) {
                    k++;
                }
            }
            System.out.println("Number of different pixels was: " + k);
            }catch(IOException e) {
            System.out.println("Exception was thrown during reading of image: " + e.getMessage());
            }

        }
}

不幸的是,两个图像像素数据经常和不可预测地不同。有人可以帮我找到一种方法,至少对于图像类型,值不会被修改吗? 编辑这是在上述过程中失败的图像

对于此图像,背景颜色已更改

4

2 回答 2

3

确保您使用正确的颜色模型进行阅读和写作。

根据BufferedImage.getRGB() 文档

从图像数据的一部分返回默认 RGB 颜色模型 (TYPE_INT_ARGB) 和默认 sRGB 颜色空间中的整数像素数组。如果默认模型与图像 ColorModel 不匹配,则会发生颜色转换。使用此方法时,返回的数据中每个颜色分量只有 8 位精度。使用图像中的指定坐标 (x, y),可以通过以下方式访问 ARGB 像素:

pixel = rgbArray[offset + (y-startY)*scansize + (x-startX)];

[编辑]

您需要使用构造函数BufferedImage(width, height, type, ColorModel),如图像类型( ) 的Javadoc 中TYPE_BYTE_BINARY所示:

当此类型用作接受 imageType 参数但没有 ColorModel 参数的 BufferedImage 构造函数的 imageType 参数时,将使用 IndexColorModel创建一个 1 位图像,该模型在默认 sRGB 颜色空间中具有两种颜色:{0, 0, 0} 和{255、255、255}。

每像素 2 或 4 位的图像可以通过BufferedImage 构造函数来构造,该构造函数通过提供具有适当地图大小的 ColorModel 来接受 ColorModel 参数。

(强调我的)

于 2013-10-01T20:02:47.857 回答
0

试试这个首先在两个数组中打印相同的索引如果结果不同意味着你的颜色模式有问题,但如果相同意味着你的比较不起作用。

于 2014-11-07T14:53:43.927 回答