【发布时间】:2013-10-06 22:46:40
【问题描述】:
今天我做了一个简单的Java应用程序,应该只是将一些.png文件加载到内存中(这些文件的总空间约为7mb),但这会产生这个奇怪的错误:
(我的小命令:java -Xmx1024m -jar dist/PNGImageLoader.jar)
已加载图像 (0) images/image_01000111100000011000000110100000 已加载 图片 (1) images/image_00000101010101101101000111111101 加载图片 (2) images/image_01001110110011110011111001000000 加载图像 (3) 图像/图像_01001111000111010110101101001111 加载图像 (4) 图像/图像_00011100000011100011001011011100 加载图像 (5) 图像/图像_01010010001010001010110110110110 加载图像 (6) 图像/图像_01101100010001000001000110101111 加载图像 (7) 图像/图像_01010111011011101010101110100010 加载图像 (8) 图像/图像_01101101110100001011001011101100 加载图像 (9) 图像/图像_01100010111110011011100001000011 加载图像 (10) 图像/图像_00011111011000111101101111101111 加载图像 (11) 图像/图像_00000100111001010110101001110001 加载图像 (12) 图像/图像_01000001100111011101101011011011 加载图像 (13) 图像/图像_01100111000010000001011101111001 加载图像 (14) 图像/图像_01101000011011000001111010001100 加载图像 (15) 图像/图像_00010010110100001011000111111000 加载图像 (16) 图像/图像_00111100111011101101101001000101 加载图像 (17) 图像/图像_01111110001010111100011000000110 加载图像 (18) 图像/图像_00010111101011100011101101101000 加载图像 (19) 图像/图像_00101000001111110110000110101101 加载图像 (20) 图像/图像_01110101110000010000000000001001 加载图像 (21) 图像/图像_01001000101010101010000010100011 加载图像 (22) 图像/图像_00110111100001110011010011011001 加载图像 (23) 图像/图像_00001010001001000001101001001011 加载图像 (24) 图像/图像_00101111000110011000110011111000 加载图像 (25) 图像/图像_00101100010101000011001101010111 加载图像 (26) 图像/图像_01101111101000010111011000011010 加载图像 (27) 图像/图像_00111011111100000111100000000011 加载图像 (28) 图像/图像_01100100000101111111001000111101 加载图像 (29) 图像/图像_01001101110111111011000101000011 加载图像 (30) 图像/图像_00110010111010000111111011100101 加载图像 (31) 图像/图像_00111001110100011100101111111011 加载图像 (32) 图像/图像_01100011101111010111110110001111 加载图像 (33) 图像/图像_01000000110111000000010100010011 加载图像 (34) 图像/图像_00110101000001001101100010101001 加载图像 (35) 图像/图像_01001101011011010110100110111010 加载图像 (36) 图像/图像_00010111010100110100011111110101 加载图像 (37) 图像/图像_01011111011001111010000000111000 加载图像 (38) 图像/图像_00110001100110011111000010110001 加载图像 (39) images/image_01110101010001111001011000000011 线程异常 “main” java.lang.OutOfMemoryError:Java 堆空间位于 java.awt.image.DataBufferByte.(DataBufferByte.java:92) 在 java.awt.image.ComponentSampleModel.createDataBuffer(ComponentSampleModel.java:415) 在 java.awt.image.Raster.createWritableRaster(Raster.java:941) 在 javax.imageio.ImageTypeSpecifier.createBufferedImage(ImageTypeSpecifier.java:1073) 在 javax.imageio.ImageReader.getDestination(ImageReader.java:2896) 在 com.sun.imageio.plugins.png.PNGImageReader.readImage(PNGImageReader.java:1280) 在 com.sun.imageio.plugins.png.PNGImageReader.read(PNGImageReader.java:1577) 在 javax.imageio.ImageIO.read(ImageIO.java:1448) 在 javax.imageio.ImageIO.read(ImageIO.java:1308) 在 pngimageloader.Images.loadImage(Images.java:22) 在 pngimageloader.Images.getImage(Images.java:33) 在 pngimageloader.Images.getAllImages(Images.java:43) 在 pngimageloader.PNGImageLoader.main(PNGImageLoader.java:15)
这是我的 PNGImageLoader.java 类,
package pngimageloader;
public class PNGImageLoader {
public static void main(String[] args) {
Images images = new Images();
images.getAllImages("images/");
}
}
这是 Images.java 类..
package pngimageloader;
import java.awt.image.BufferedImage;
import java.io.File;
import java.util.HashMap;
import javax.imageio.ImageIO;
public class Images {
HashMap images;
Images() {
images = new HashMap();
}
BufferedImage loadImage(String path) {
try {
return ImageIO.read(new File(path));
} catch (Exception exception) {
System.out.println(exception.getMessage());
System.exit(1);
return null;
}
}
BufferedImage getImage(String path) {
BufferedImage image = (BufferedImage) images.get(path);
if (image == null) {
image = loadImage(path);
images.put(path, image);
}
return image;
}
void getAllImages(String path) {
File files = new File(path);
int i = 0;
for (File file : files.listFiles()) {
getImage(file.getPath());
System.out.println("Loaded image (" + i + ") " + file.getPath());
i++;
}
}
}
我不专业,但我认为这真的很奇怪。 提前感谢您的帮助,帕特里克。
【问题讨论】:
-
怎么奇怪?您正在从内存中的磁盘加载一堆图像。内存是有限的。因此它会抛出 OutOfMemoryError,因为它没有足够的内存来加载所有图像。
-
@PerdutaPatrick 128mb 是一个比人们想象的更容易打破的障碍。
-
部分问题在于 PNG 是一种压缩文件格式。因此,一旦加载到 BufferedImage 中,以像素为单位的文件大小可能远远大于 7mb。我刚刚在 Photoshop 中创建了一个 1000x1000 纯色图像(1M 像素 x 3 字节/像素),但 PNG 文件的大小只有 1kb。
-
您为整个 JVM 堆分配了最大 128 MB 的空间。这为图像留下了很小的空间(远少于您的 2GB 内存)。尽管它们以 PNG 压缩形式在磁盘上只占用 7 MB,但它们在内存中占用了更多空间,它们在内存中是未压缩的并以可渲染的方式表示。
-
我的手机有 1 GB 的可用内存(和 70 GB 的可用存储空间)。如果您的机器在进行内存密集型测试时没有更多内存,请购买适合该工作的机器。
标签: java image out-of-memory