如何将图像保存到 zip 文件中
我正在尝试读取流并将读取的图像保存到 zip 文件中,因为这将运行多天并且会生成太多单独的文件。
我现在遇到一个问题,似乎无法将图像保存到 zip 文件中。我为其构建的工作线程如下。我确信图像正在进入 ImageIO.write。然而,最终的结果是一个空 jpg 的 zip 文件。我想知道 ImageIO 是否没有将属性写入 ZipOutputStream。
感谢您的帮助。
public class ZipSaveWorker implements Runnable{
public static ZipOutputStream out=null;
BufferedImage myImage;
private static int counter=0;
public void run() {
ZipEntry entry=new ZipEntry("video"+counter+".jpg");
counter++;
try {
out.putNextEntry(entry);
ImageIO.write(myImage, ".jpg", out);
} catch (IOException ex) {
Logger.getLogger(ZipSaveWorker.class.getName()).log(Level.SEVERE, null, ex);
}
}
public ZipSaveWorker(BufferedImage image)
{
if (out==null)
{
try {
out = new ZipOutputStream(new BufferedOutputStream(new FileOutputStream(new File("images" + File.separator + "video.zip"))));
} catch (FileNotFoundException ex) {
Logger.getLogger(ZipSaveWorker.class.getName()).log(Level.SEVERE, null, ex);
}
counter=0;
}
myImage=image;
}
public static void closeStream()
{
try {
out.flush();
out.close();
} catch (IOException ex) {
Logger.getLogger(ZipSaveWorker.class.getName()).log(Level.SEVERE, null, ex);
}
}
}
I am attempting to read in a stream and save the read images to a zip file as this is going to be running over multiple days and would generate far too many individual files.
I now have an issue where I seem to be unable to save images into a zip file. The worker thread I have built for it is below. I am sure that the image is making it to the ImageIO.write. The result at the end however is a zip file of empty jpgs. I am wondering if perhaps ImageIO is not writing property to the ZipOutputStream.
Thanks for your help.
public class ZipSaveWorker implements Runnable{
public static ZipOutputStream out=null;
BufferedImage myImage;
private static int counter=0;
public void run() {
ZipEntry entry=new ZipEntry("video"+counter+".jpg");
counter++;
try {
out.putNextEntry(entry);
ImageIO.write(myImage, ".jpg", out);
} catch (IOException ex) {
Logger.getLogger(ZipSaveWorker.class.getName()).log(Level.SEVERE, null, ex);
}
}
public ZipSaveWorker(BufferedImage image)
{
if (out==null)
{
try {
out = new ZipOutputStream(new BufferedOutputStream(new FileOutputStream(new File("images" + File.separator + "video.zip"))));
} catch (FileNotFoundException ex) {
Logger.getLogger(ZipSaveWorker.class.getName()).log(Level.SEVERE, null, ex);
}
counter=0;
}
myImage=image;
}
public static void closeStream()
{
try {
out.flush();
out.close();
} catch (IOException ex) {
Logger.getLogger(ZipSaveWorker.class.getName()).log(Level.SEVERE, null, ex);
}
}
}
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
您的代码中的错误在行中:
应该是:
我也不确定是否应该在写入每个图像后调用 closeEntry() 。
考虑一下 Stephen C 所写的内容,如果断电或虚拟机死机,此代码可能会导致 zip 文件损坏。考虑每周备份几次 zip 文件,甚至每天备份几次,以确保您的多日运行不会完全毁掉(我假设运行可以恢复)。
The error in your code is in the line:
It should be:
I am also not sure if you should call closeEntry() after every image has been written.
Consider what Stephen C writes, this code could result in corrupt zip files if the power was cut or the VM died. Consider making backups of the zip files a few times a week, maybe even a few times a day, to ensure your multiple day runs aren't completely ruined (I assume a run can be resumed).
我不相信这个推理。文件的实际数量应该没有那么重要。每个文件可能会平均损失 1/2 个(文件系统)磁盘块,但对于花费几百美元的 TB 磁盘驱动器来说,这可能微不足道。
但更重要的问题是,如果您的应用程序...或电源关闭,会发生什么情况。如果您将所有图像直接写入 ZIP 文件,那么在多天的运行中,您最终可能会得到一个损坏的 ZIP 文件。我预计 ZIP 文件内容大部分是可恢复的,但只能使用某些第三方(非 Java)应用程序。
如果文件系统资源(磁盘空间、索引节点数量等)是一个现实问题,那么也许您应该编写一个脚本来每小时运行一次并压缩写入的文件最后一个小时,(也许)将 ZIP 文件放在其他地方。
I'm not convinced by this reasoning. The actual number of files should not really matter that much. You might lose on average 1/2 a (file system) disk block per file, but with terabyte disc drives available for a couple of hundred dollars, that's probably insignificant.
But the more important problem is what happens if your application ... or the power goes off. If you write all of your images straight into a ZIP file, the chances are that you will end up with nothing but a corrupt ZIP file for a multi-day run. I expect that the ZIP file contents will be mostly recoverable, but only using some third party (non-Java) application.
If file system resources (disk space, number of inodes, whatever) are a realistic concern, then maybe you should write a script to run (say) once an hour and ZIP up the files that were written in the last hour and (maybe) put the ZIP file somewhere else.