我们的系统使用了很多大型Bitmaps(System.Drawing.Bitmap),有时我们的内存不足并导致“参数无效”错误。这是有道理的,因为很难分配大量连续的内存块。
所以问题是......如果我们将系统升级到64位,这个问题会消失吗?
答案 0 :(得分:3)
如果这是一个内存分配问题(由于大对象堆碎片,很可能会在加载20个左右图像后分配100MB块时遇到问题,即使有些它们随后被卸载了,然后移动到64位应该有所帮助 - 更大的地址空间应该给堆充足的工作空间,从而缓解症状。
内存问题应该产生一个OutOfMemoryException,但是.net中的位图处理代码可能会捕获这个并有效地转换为InvalidParameterException。但是,有可能存在与图像的大小/格式有关的另一个问题,并且它确实是无效参数。
答案 1 :(得分:1)
通常,当你开始在内存中使用巨大的位图时,你总会遇到这种问题。避免这种情况的最佳方法是将图像分割成数组或类似的东西,以便创建网格。
从那时起,您只需要/必须在屏幕上加载可以查看的内容,这样可以节省大量内存。
当我决定制作一些游戏来杀人时,我发生了这种情况。
我决定创建一个Maze / Pipe游戏,用户可以选择列数和行数。我决定将图像限制为10000px×10000px。
我的第一次尝试,我确切地说你的问题。错误发生后出错,主要是内存问题。
我决定做一些关于如何做我想做的研究,并找到了解决方案。
我所做的是创建了一个动态的二维数组(我决定将其限制为最大值1000乘以1000),我只是将它们放入小的10x10像素图像或用户决定的任何内容。
当这样做时,内存/加载速度等等的问题就消失了。
我的修复之前的内存使用量很容易超过一个演出,当你使用限制时,现在应用程序的内存使用量在150到225兆内拉
如果您想尝试一下,请下载此内容并查看菜单(迷宫)并使用以下设置进行播放:my little games
答案 2 :(得分:1)
根据Bitmap的创建方式,使用DDB还是DIB视频内存或使用系统内存(DDB使用视频内存,DIB的系统内存)。你必须使用DotNet reflector来确定每个创建时间取决于你使用的构造函数...例如,当你去的时候创建一个DDB:
var bmp = new Bitmap(width, height, pixelDepth)
并且在具有小型视频卡的计算机(即您可能正在运行Web服务的服务器)上的大小限制为5000x5000,而您可以发现可以使用
加载10000x10000位图var bmp = new Bitmap(pathToLargeFilename);
我没有太多运气搞清楚如何强制创建DIB in Dotnet(我的猜测是最简单的方法是手动创建Bitmap结构,手动分配内存,然后以某种方式将其转换为一个位图。也许你最好的选择是转移到一个不使用视频内存的备用成像库(有很多开源的FreeImage,ImageMagick,Cairo (尽管你必须至少从Mono获得GTK packages才能运行)
答案 3 :(得分:0)
前一段时间,在Vista 64位系统上使用Visual Studio 2008进行开发时,我经常遇到这种错误。所以我想进入64Bit可能会增加成功的机会并使错误发生的次数减少,但我不会认为转移到64位会完全治愈它。
帮助我的是这个链接: http://confluence.jetbrains.net/display/ReSharper/OutOfMemoryException+Fix
它是一个替换内存分配策略的包装器,s.t。你倾向于获得更大的连续内存块。也许你可以在你的应用程序中使用类似的内存分配策略,因为这个策略应该只包装visual studio。
答案 4 :(得分:0)
您可以在系统上创建多大的位图是有限制的。
查看http://www.efg2.com/Lab/Graphics/VeryLargeBitmap.htm以查找可以显示系统限制的程序。
也许你正在达到这个极限。
答案 5 :(得分:0)
在分配这些大位图之前,您可以尝试调用GC.Collect()。我最近遇到了这个问题,这有帮助。 (我的第一反应也是转移到64位,但添加一行代码有点简单。; - )