gpt4 book ai didi

java - 将缓冲图像转换为具有相同数据的二维字节数组

转载 作者:行者123 更新时间:2023-12-03 19:02:19 25 4
gpt4 key购买 nike

我用 Java 编写了一个图像处理应用程序。我已经处理了作为缓冲图像的图像,现在我想为处理过的图像返回 byte[],我应该得到二值化图像的字节数组。

这是我的代码:

public static byte[][] binarizeImage(BufferedImage bfImage){

int red;
int newPixel;
int h ;
int w ;
int threshold = otsuTreshold(bfImage);
// this function returns the threshold value 199

BufferedImage binarized = new BufferedImage(bfImage.getWidth(), bfImage.getHeight(), bfImage.getType());

for(int i=0; i<bfImage.getWidth(); i++) {
for(int j=0; j<bfImage.getHeight(); j++) {

// Get pixels
red = new Color(bfImage.getRGB(i, j)).getRed();
int alpha = new Color(bfImage.getRGB(i, j)).getAlpha();
if(red > threshold) {
newPixel = 255;
}
else {
newPixel = 0;
}
newPixel = colorToRGB(alpha, newPixel, newPixel, newPixel);
binarized.setRGB(i, j, newPixel);
}

}
Raster raster = binarized.getData();

h = raster.getHeight();
w = raster.getWidth();

byte[][] binarize_image = new byte[w][h];

for(int i=0 ; i<w ; i++)
{
for(int j=0; j<h ; j++)
{
binarize_image[i][j]=raster.getSampleModel(); //error at this line
}
}
return binarize_image;
}

// Convert R, G, B, Alpha to standard 8 bit
private static int colorToRGB(int alpha, int red, int green, int blue) {

int newPixel = 0;
newPixel += alpha;
newPixel = newPixel << 8;
newPixel += red; newPixel = newPixel << 8;
newPixel += green; newPixel = newPixel << 8;
newPixel += blue;

return newPixel;

}

但它不起作用。我应该怎么做才能将该缓冲图像转换为相同图像数据的字节数组?

最佳答案

我不确定术语“二值化”在这种情况下是什么意思。您似乎只想过滤图像(即根据某个阈值切断红色 channel )并将结果转换为 byte[]

假设以上是正确的,然后检查下面的代码。它会将图像转换为 32 位图像的 byte[]。请考虑以下事项:

  • 您不需要先过滤图像然后再转换为byte[]。您可以在转换期间执行此操作。
  • “将 RGB 转换为标准 8 位”:如果您的意思是 每个颜色 channel 8 位,那么这没问题,但如果您的意思是 8 位 per pixel 然后你在谈论压缩/转换(即你可能会丢失一些信息/质量)在这种情况下你应该提供更多关于你想要实现的信息。
  • 您生成的 byte[] 的大小将是 4 * width * height 而不是 width * height 假设我们正在讨论这种情况的 32 位图像。如果您需要处理其他情况,您应该考虑 BufferedImage 支持的可用图像类型(或者至少只考虑您感兴趣的图像类型)。

下面的代码将打印每个转换像素的信息,如下所示(注意红色 channel 是如何过滤的):

[0,0] 转换 [ffaaccee] --> [0, cc, ee, ff]

package imageio.byteconversion;

import java.awt.image.BufferedImage;
import java.io.IOException;
import java.io.InputStream;
import javax.imageio.ImageIO;

public class BufferedImageToBytes {

private static void log(String s) {
System.out.println(s);
}

private static String toByteString(int color) {
// Perform a bitwise AND for convenience while printing.
// Otherwise Integer.toHexString() interprets values as integers and a negative byte 0xFF will be printed as "ffffffff"
return Integer.toHexString(color & 0xFF);
}

public static void main(String[] args) throws IOException {

// Load the image. This expects the image to be in the same package with this class
InputStream stream = BufferedImageToBytes.class.getResourceAsStream("test.png");
BufferedImage image = ImageIO.read(stream);
int iw = image.getWidth();
int ih = image.getHeight();
log("Image loaded succesfully, width=" + iw + " height=" + ih);
stream.close();

log("Image color model: " + image.getColorModel());
log("Image sample model: " + image.getSampleModel());
log("Image raster: " + image.getRaster());

int bands = image.getSampleModel().getNumBands();
log("Color bands: " + bands);
if (bands != 4) {
throw new RuntimeException("The image does not have 4 color bands. Are you sure this is a 32-bit image?");
}

int threshold = 199; // <-- decide your threshold here

byte bytes[] = new byte[4 * iw * ih];
int index = 0;

// note that image is processed row by row top to bottom
for(int y = 0; y < ih; y++) {
for(int x = 0; x < iw; x++) {

// returns a packed pixel where each byte is a color channel
// order is the default ARGB color model
int pixel = image.getRGB(x, y);

// Get pixels
int alpha = (pixel >> 24) & 0xFF;
int red = (pixel >> 16) & 0xFF;
int green = (pixel >> 8) & 0xFF;
int blue = pixel & 0xFF;

// perform filtering here depending on threshold
if (red > threshold) {
red = 255;
} else {
red = 0;
}

log("[" + x + "," + y + "]" + " Converting [" + Integer.toHexString(pixel) + "] --> ["
+ toByteString(red) + ", " + toByteString(green) + ", "
+ toByteString(blue) + ", " + toByteString(alpha)
+ "]");

bytes[index++] = (byte) red;
bytes[index++] = (byte) green;
bytes[index++] = (byte) blue;
bytes[index++] = (byte) alpha;
}
}
}
}

关于java - 将缓冲图像转换为具有相同数据的二维字节数组,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18503412/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com