0

我在通过 ForkJoinPool 加载大量图像时遇到问题,我正在使用超线程的 4 核 Intel 进行测试,因此有 8 个逻辑线程。但是,我将池限制为只有 4 个线程。我收到来自 ImageIO 的错误,无法找到图像。

public class LoadImages extends RecursiveAction {
private static final long serialVersionUID = 1L;

//this is an example
private static int threadThreshold = totalImages/totalThreads + 2;

private String[] imgArr;
private int arrStart = 0;
private int arrSize = 0;

public LoadImages(String[] imgs, int start, int size) {
    imgArr = imgs;
    arrSize = size;
    arrStart = start;
}

protected void processImages(){
    BufferedImage img = null;
    for (int i = arrStart; i < arrStart + arrSize; i++) {
        try{
            img = ImageIO.read(new File(imgArr[i]));    
        } catch (IOException | CMMException | NullPointerException e) {
            System.out.println(imgArr[i]);
            e.printStackTrace();
            img = null;
        }

        ...

    }
}

protected void compute() {
    // Check the number of files
    if (arrSize <= threadThreshold) {
        processImages();
        return;
    } else {

        int split = arrSize / 2;

        invokeAll(new LoadImages(imgArr, arrStart, split), new LoadImages(imgArr, arrStart + split, arrSize - split));
    }

}
}

任何关于我做错了什么的见解都会很棒,我注意到它真的只有在我有超过 1700 张图像并且所有图像都超过 5MB 时才会中断。

这是我从 Java 收到的错误:

javax.imageio.IIOException: Can't create an ImageInputStream!
at javax.imageio.ImageIO.read(Unknown Source)

当我知道文件在那里时。我将此代码用作指南: https ://docs.oracle.com/javase/tutorial/essential/concurrency/forkjoin.html

4

3 回答 3

0

似乎有点随机。我的猜测是它可能只是硬件或操作系统错误。假设这是一个缩放问题,我对你的 1700 多张图像的建议是,你最好将它设置在云端的某个地方 - 可以节省大量时间和头痛

于 2014-12-11T20:27:52.760 回答
0

在我看来,当它在内部创建 ImageInputStream 时出现 ImageIO 错误。您是否尝试使用 ImageInputStream 读取图像?喜欢:

InputStream is = new FileInputStream("path");
ImageInputStream iis = ImageIO.createImageInputStream(is);
BufferedImage bufImage = ImageIO.read(iis);
于 2014-12-11T20:49:28.630 回答
-1

如果你去检查源代码ImageIO.read(File)ImageIO.read(ImageInputStream)你可以看到它ImageIO重用了 的实例ImageReader,而这篇文章说这ImageReader不是线程安全的。您可能必须创建自己的ImageReaders以便在单独的线程中使用。

此外,您还应该衡量这种多线程 IO 策略真正为您带来的收益。如果您试图从旋转的硬盘驱动器中提取大量图像数据,您的进程可能会受到 I/O 限制,并且并行加载不会给您带来太多好处。

于 2014-12-11T20:40:13.247 回答