Java 如何同时计算三幅图像的像素数

Java 如何同时计算三幅图像的像素数,java,Java,如何同时计算三幅图像的总像素? 我尝试使用java Swing Worker和线程,我得到了答案,但返回指定范围的总像素计数(每个图像30秒,图像大小480*303)需要1.30分钟。但我需要在30秒内同时得到三张图片的答案 public class ImageProcessor1 implements Runnable{ static int blackPix=0; BufferedImage tempImg; public static int blackPixel=0; public Im

如何同时计算三幅图像的总像素? 我尝试使用java Swing Worker和线程,我得到了答案,但返回指定范围的总像素计数(每个图像30秒,图像大小480*303)需要1.30分钟。但我需要在30秒内同时得到三张图片的答案

public class ImageProcessor1 implements Runnable{
static int blackPix=0;
BufferedImage tempImg;
public static int blackPixel=0;
public ImageProcessor1(String path) throws Exception{
tempImg = ImageIO.read(new File(path));
}

private static int[] getPixelData(BufferedImage img, int x, int y) {
    int argb = img.getRGB(x, y);

    int rgb[] = new int[]{
        (argb >> 16) & 0xff, //red
        (argb >> 8) & 0xff, //green
        (argb) & 0xff //blue
    };
    System.out.println("Process1 :rgb: " + rgb[0] + " " + rgb[1] + " " + rgb[2]);
    return rgb;
}

@Override
public void run() {
     int[][] pixelData = new int[tempImg.getHeight() * tempImg.getWidth()][3];
        int[] rgb;
        int height=tempImg.getHeight();
        int width=tempImg.getWidth();
        int counter = 0;
        for (int i = 0; i < width; i++) {
            for (int j = 0; j < height; j++) {
                rgb = getPixelData(tempImg, i, j);
                if(rgb[0]<125 && rgb[0]>105 && rgb[1]<125 && rgb[1]>105 && rgb[2]<125 && rgb[2]>105)
                {
                    blackPixel+=1;
                }
            }
        }
}
公共类ImageProcessor1实现可运行{
静态int blackPix=0;
缓冲图像时间;
公共静态int blackPixel=0;
公共ImageProcessor1(字符串路径)引发异常{
tempImg=ImageIO.read(新文件(路径));
}
私有静态int[]getPixelData(BuffereImage img,int x,int y){
int argb=img.getRGB(x,y);
int rgb[]=新的int[]{
(argb>>16)&0xff,//红色
(argb>>8)&0xff,//绿色
(argb)&0xff//蓝色
};
System.out.println(“进程1:rgb:+rgb[0]+”“+rgb[1]+”“+rgb[2]);
返回rgb;
}
@凌驾
公开募捐{
int[][]pixelData=new int[tempImg.getHeight()*tempImg.getWidth()][3];
int[]rgb;
int height=tempImg.getHeight();
int width=tempImg.getWidth();
int计数器=0;
对于(int i=0;i

}

很奇怪,在这么小的一张图片上迭代需要30秒

在进行了一些分析之后,似乎在热循环中使用println语句会显著降低速度

对代码稍作修改后,10500x5788映像在我的机器上拍摄约3秒

修改后的版本:

package application;

import java.awt.image.BufferedImage;
import java.io.File;
import java.util.concurrent.TimeUnit;

import javax.imageio.ImageIO;

public class ImageProcessor1 implements Runnable {

  BufferedImage tempImg;
  public static int blackPixel = 0;

  public ImageProcessor1(final String path) throws Exception {
    final long start = System.nanoTime();

    tempImg = ImageIO.read(new File(path));
    // Use tracing, profiling and sampling to proof performance issues and fixes
    System.out.println("ImageIO took " + TimeUnit.NANOSECONDS.toMillis(System.nanoTime() - start)
        + " ms.");
  }

  @Override
  public void run() {
    long start = System.nanoTime();
    final int height = tempImg.getHeight();
    System.out.println("Getting height '" + height + "' took "
        + TimeUnit.NANOSECONDS.toMillis(System.nanoTime() - start) + " ms.");


    start = System.nanoTime();
    final int width = tempImg.getWidth();
    System.out.println("Getting width '" + width + "' took "
        + TimeUnit.NANOSECONDS.toMillis(System.nanoTime() - start) + " ms.");

    start = System.nanoTime();

    // reuse variables
    int argb;
    int red;
    int green;
    int blue;

    for (int i = 0; i < width; i++) {
      for (int j = 0; j < height; j++) {
        // HOT LOOP. Do as little as possible. No println calls!
        argb = tempImg.getRGB(i, j);

        // inline all method calls
        red = argb >> 16 & 0xff; // red
        green = argb >> 8 & 0xff; // green
        blue = argb & 0xff; // blue

        if (red < 125 && red > 105 && green < 125 && green > 105 && blue < 125 && blue > 105) {
          blackPixel += 1;
        }
      }
    }
    System.out.println("Iterating pixels took "
        + TimeUnit.NANOSECONDS.toMillis(System.nanoTime() - start) + " ms.");
  }

  public static void main(final String[] args) throws Exception {
    new ImageProcessor1("big.jpg").run();
    System.out.println("Number of blackpixels = " + blackPixel);
  }

}
包应用;
导入java.awt.image.buffereImage;
导入java.io.File;
导入java.util.concurrent.TimeUnit;
导入javax.imageio.imageio;
公共类ImageProcessor1实现可运行{
缓冲图像时间;
公共静态int blackPixel=0;
公共ImageProcessor1(最终字符串路径)引发异常{
最终长启动=System.nanoTime();
tempImg=ImageIO.read(新文件(路径));
//使用跟踪、分析和采样来证明性能问题和修复
System.out.println(“ImageIO耗时”+时间单位.NANOSECONDS.toMillis(System.nanoTime()-start)
+“女士”);
}
@凌驾
公开募捐{
长启动=System.nanoTime();
final int height=tempImg.getHeight();
System.out.println(“获取高度”+“高度”+“'take”
+TimeUnit.NANOSECONDS.toMillis(System.nanoTime()-start)+“ms.”;
start=System.nanoTime();
final int width=tempImg.getWidth();
System.out.println(“获取宽度”’+width+“'take”
+TimeUnit.NANOSECONDS.toMillis(System.nanoTime()-start)+“ms.”;
start=System.nanoTime();
//重用变量
int-argb;
红色;
绿色;
蓝色;
对于(int i=0;i>16&0xff;//红色
绿色=argb>>8&0xff;//绿色
蓝色=argb&0xff;//蓝色
如果(红色<125&&red>105&&green<125&&green>105&&blue<125&&blue>105){
黑像素+=1;
}
}
}
System.out.println(“迭代像素”
+TimeUnit.NANOSECONDS.toMillis(System.nanoTime()-start)+“ms.”;
}
公共静态void main(最终字符串[]args)引发异常{
新的ImageProcessor1(“big.jpg”).run();
System.out.println(“黑像素数=”+blackPixel);
}
}
更一般地说,您必须小心您的方法,因为您将所有图像读入RAM,然后处理它。如果同时对3个或更多大图像执行此操作,则有可能出现OutOfMemory错误。如果这成为一个问题,您可以将图像作为输入流读入,一次只处理图像的小缓冲区

要了解如何做到这一点,请参见


要了解如何累积多个线程的输出,请参阅。

向我们展示一些代码?为什么要花30秒才能返回一张图像的总像素数?你的问题有误导性。听起来好像你想计算三幅图像中所有像素的总数。但从你的代码来看,你似乎在试图计算所有三幅图像中特定像素值范围的数量。先生,我实际上是在计算给定范围内的像素。它的工作,但我想知道它是如何可能得到总计数在同一时间。这是一个实时过程的一部分,所以我需要比较三个计数,我需要至少三个