VB.net GDI+ 内存不足,一般性错误,对象错误等解决方案和优化代码。

最近由于要处理大量图像并将图像拼接为一个大图形,每个图像像素都很大(1280x960),拼接后更大,并且需要对图像频繁进行标记等操作,遇到了很多问题,内存不足,一般性错误,对象错误等等等等。

通过自己的摸索与在网上查找相应网友的经验,自己总结了一套相对较好的代码,满足了自己的需要,并且目前较为稳定的运行。代码并不是最优化,肯定还有更好的解决方法。欢迎大家给出意见和建议。

下面代码中标记出了常见的问题知识点,我先上代码,随后一一解释

       Try

            '----------------知识点一:打开源文件,建立新图像,复制源文件到新图像,释放源文件
		   '案例 http://www.cnblogs.com/yeahgis/archive/2011/11/12/2246332.html
		   '案例 http://blog.csdn.net/gisoracle/article/details/4961511
<pre class="vb" name="code">            '打开源文件
            Dim imageFile As Image = Image.FromFile(strFileLocation + "\JPG\FULL.jpg")
            Dim destGraphic As System.Drawing.Graphics = System.Drawing.Graphics.FromImage(imageFile)
	    '操作image
            destGraphic.DrawImage(otherimage, 0, 0)
             '释放
             destGraphic.Dispose()
             imageFile.Dispose()

	    '将图像加载到Picturebox 
             imgMaster.Image = CType(imageFile.Clone, Image) 
            '保存文件为另外名称 imageFile.Save(AOI_BlockVSRefVIEWER.strFileLocation + "\FOVCOMBINEImages\FULLnew.jpg", AOI_FOV.GetImageFormat("jpg"))                
            System.Windows.Forms.Application.DoEvents() 
            '--------------------知识点二: 注意释放内存资源----------------- 
            '释放源文件防止再操作时忙碌 
             imageFileTemp.Dispose() 
             '释放Graphic缓解系统内存紧张 
             destGraphic.Dispose() 

             '-----------------知识点三: 不要释放picturebox所引用的图像,否则你在该应用程序与其他系统应用程序切换多次后会引起错误。 
             'imageFile.Dispose() 

             '-----------------知识点四:很多情况即使dispose了仍然内存不足,启用强制垃圾回收大大缓解了 
             'http://blog.sina.cn/dpool/blog/s/blog_700bf71601018wq6.html?vt=4 
             GC.Collect() 
        Catch ex As Exception 
             '-----------------知识点五: GDI+一些错误很奇特,只有简单的一般错误提示,而用Marshal这个才能得到有价值的错误信息 
             '参见http://wenku.baidu.com/view/3cf9556d4afe04a1b171de32.html 
             Marshal.GetLastWin32Error() 
End Try

知识点一:

            很多情况下大家都使用简单的步骤加载图片: 打开源文件赋值给image-> 建立Graphic并对image进行操作->释放Graphic和Image。

一般方法:
		   '打开图像文件
            Dim imageFile As Image = Image.FromFile(strFileLocation + "\FOVCOMBINEImages\FULL.jpg")
            Dim destGraphic As System.Drawing.Graphics = System.Drawing.Graphics.FromImage(imageFile)
		   '操作图像文件
            destGraphic.DrawImage(otherimage, 0, 0)
		   '释放
		   destGraphic.Dispose()
		   imageFile.Dispose()


这种方式大部分情况下不会出现问题,但当图像文件比较大,频繁操作同一个图像时,会发生一般性错误,或者指示文件被其他程序占用。所以采用代码改良后的方法给系统一定缓冲,极大减少了一般性错误和文件被占用的错误产生


知识点二:

          这个比较简单,一般大家都有注意,提示内存不足时请务必查看自己是否Dispose了不需要的资源


知识点三:

         这个比较容易忽略。 如果窗体上有一个picturebox,你加载了图片,在处理完后你将image给释放掉了,一般情况下不会出现问题,即使你dispose了那个image,系统会暂存到picturebox中。 当如果图片过大,系统会在有些时候释放掉。 比方你在打开该窗口后,去执行操作系统下的其他软件或程序,系统根据内存分配会将Picturebox那个清空,当你操作完其他程序后转来点这个窗口时系统会重载picturebox的image,但image已经被你Dispose了,会出现对象错误的情况。 解决方法就是让该图片驻留到内存,不要Dispose。


知识点四:

         当图片实在很大很多,或者一些特殊的情况下,将所有都Dispose掉了仍然会有内存不足,或者一般性错误,这时尝试启用强制垃圾回收GC.collect()


知识点五:

         这是使用GDI+比较无语的一个Exception, 里面什么信息都没有。我们可以调用Marshal这个来获取有意义的错误信息。



评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值