c#picturebox内存释放问题
我是C#的新手。 我必须在工作线程中重复刷新GUI图片框。 从使用GetImage方法轮询驱动程序的相机获取图像,该方法检索要显示的图像。 即使我使用指令“using”分配位图并显式调用GC,内存似乎永远不会被释放。
工作线程是这样的:
while (true) { // request image with IR signal values (array of UInt16) image = axLVCam.GetImage(0); lut = axLVCam.GetLUT(1); DrawPicture(image, lut); //GC.Collect(); }
虽然DrawPicture方法是类似的
public void DrawPicture(object image, object lut) { [...] // We have an image - cast it to proper type System.UInt16[,] im = image as System.UInt16[,]; float[] lutTempConversion = lut as float[]; int lngWidthIrImage = im.GetLength(0); int lngHeightIrImage = im.GetLength(1); using (Bitmap bmp = new Bitmap(lngWidthIrImage, lngHeightIrImage)) { [...many operation on bitmap pixel...] // Bitmap is ready - update image control //SetControlPropertyThreadSafe(tempTxtBox, "Text", string.Format("{0:0.#}", lutTempConversion[im[160, 100]])); //tempTxtBox.Text = string.Format("{0:00000}", im[160, 100]); //System.Drawing.Image.FromHbitmap(bmp.GetHbitmap()); pic.Image = System.Drawing.Image.FromHbitmap(bmp.GetHbitmap()); } }
问题出现了
pic.Image = System.Drawing.Image.FromHbitmap(bmp.GetHbitmap());
事实上,评论这行代码,垃圾收集工作就像它一样。 更好的是,问题似乎与之相关
System.Drawing.Image.FromHbitmap(bmp.GetHbitmap())
有什么建议来解决这个内存泄漏?
非常感谢!
Image
实现了IDisposable
,因此您应该在不再需要的每个Image
实例上调用Dispose
。 您可以尝试在代码中替换此行:
pic.Image = System.Drawing.Image.FromHbitmap(bmp.GetHbitmap());
有了这个:
if (pic.Image != null) { pic.Image.Dispose(); } pic.Image = System.Drawing.Image.FromHbitmap(bmp.GetHbitmap());
这将在分配新图像之前处理先前的图像(如果有的话)。
问题是,你正在用GetHbitmap制作一个bmp
的GDI位图,根据msdn:
您负责调用GDI DeleteObject方法来释放GDI位图对象使用的内存。
然后FromHbitmap方法复制GDI位图; 因此,您可以在创建新图像后立即使用GDI DeleteObject方法释放传入的GDI位图。
所以基本上我会添加:
[System.Runtime.InteropServices.DllImport("gdi32.dll")] public static extern bool DeleteObject(IntPtr hObject); ... IntPtr gdiBitmap = bmp.GetHbitmap(); // Release the copied GDI bitmap if (pic.Image != null) { pic.Image.Dispose(); } pic.Image = System.Drawing.Image.FromHbitmap(gdiBitmap); // Release the current GDI bitmap DeleteObject(gdiBitmap);
我不确定你是否需要GDI位图来执行某种转换。 如果不这样做,您只需将位图分配给PictureBox的Image属性,并忽略以前的解决方案:
// Since we're not using unmanaged resources anymore, explicitly disposing // the Image only results in more immediate garbage collection, there wouldn't // actually be a memory leak if you forget to dispose. if (pic.Image != null) { pic.Image.Dispose(); } pic.Image = bmp;
有几种方法可以从pbox中释放图像。 我强烈建议的方法是不要使用pbox.Image = Image.FromFile...
如果你不使用FileStream,你想从文件中读取它使用BitMap类。 像这样:
Bitmap bmp = new Bitmap(fileName); pbox.Image = bmp; // notice that we used bitmap class to initialize pbox.
…然后你要释放图像文件bmp.Dispose();
现在您可以删除,移动或任何您想要的文件。
- 我可以在.net 4中部署我的ASP.NET MVC 4应用程序
- UdpClient.ReceiveAsync正确提前终止
- 应该“或”使用.Net4 Hasflags:enum.HasFlag(AccessRights.Read | AccessRights.Write)
- MVC4将模型绑定到ICollection或List in partial
- .Owner属性和ShowDialog(IWin32Window所有者)之间的区别?
- 我们可以向ServicePointManager.SecurityProtocol添加四个协议吗?
- 如何处理多个相同的MIDI USB设备
- 动态代码片段c#visual studio
- 使用System.Data.SQLite.SQLIteDataReader.GetBlob检索BLOB字段时出错