2015-04-17 87 views
1

在我的应用程序中,我正在处理大约30-70张大图片。通过工作我的意思是加载,裁剪,调整大小和添加到aviStream。每个图像可以有高达4500p和10MB(使用这种大图像可以解决大部分内存不足的例外情况)。在测试时,我有时会使用较小的(每个2500p〜500kB),并且内存情况要好得多。g.DrawImage抛出内存异常

我已经改变了我的程序体系结构:加载一个图像,处理所需的操作,将其添加到流,关闭它。并在下一张图片上做同样的事情。但由于代码的复杂性和大小,我不能100%确定我在此过程中处理和关闭为临时目的而创建的每个位图和图像。

我有以下错误:裁剪图像时

An unhandled exception of type 'System.OutOfMemoryException' occurred in System.Drawing.dll 

一般:

public static Image Crop(Image imgPhoto, Point xy, int width, int height) { 
     Rectangle cropRect = new Rectangle(xy, new Size(width, height)); 
     Bitmap target = new Bitmap(cropRect.Width, cropRect.Height); 

     using (Graphics g = Graphics.FromImage(target)) { 
      g.DrawImage(imgPhoto, new Rectangle(0, 0, target.Width, target.Height), cropRect, GraphicsUnit.Pixel); 
     } 

     return target; 
    } 

唯一的例外是基于种植水平抛出,如果我裁剪的大图像的一小部分,让在中间说800x600像素,这是更好的。如果以相反的方式裁剪裁剪,比方说在原始图像较小的情况下创建3500x2500图像(空白区域会自动填充所选颜色),但我大多数情况下都有例外。

一个有趣的事情是,在第23张图像周围引发了异常,所以以前的图像处理得很好。

你们可以给我一个建议如何调试吗?我试图扫描未置放的图像和位图的代码,但似乎我没有找到所有这些。

因此,最大的问题是:如何逐一处理所有图像而没有异常?

+0

我会说这是一个Dispose问题,但如何轻松找到它们......这是另一回事。 –

+0

好吧,'Bitmap'没有被放置,它从函数返回。我假设调用代码也不会处理它。此外,如果您正在处理许多大型图像,可能会尝试重新使用缓冲区,而不是重新分配缓冲区。 – svinja

+0

我部分重用它们,但我也有很多这样的方法,我在一些更改后返回原始输入图像。如果我是正确的,在这种情况下只有一个图像,只有一个参考正在发送。所以我无法处理它,否则我会失去原始数据,对吧? – pheno

回答

1

如果你想创建你必须使用using块的方法之外的方法中的位图,我的意思是,你调用的方法是这样的:

using (var myNewBitmap = Crop(imgPhoto, xy, width, height)) 
{ 

// do whatever you want with the bitmap 

} 

的使用,将处理后你不会得到例外。使用当前的代码,您可以在将来获得内存不足。

+0

好 - 这是比OP说他们在对他们的问题发表评论时所做的更清晰的解决方案。 (注释说在原始位图上添加了Dispose而不是在返回的位图上;没有看到他们的调用代码,就不可能知道为什么这是成功的......) – ToolmakerSteve