[问题] 程式使用内存的上限

楼主: googled (15357)   2014-05-21 02:19:26
各位好,小弟用Qt Creator写了一个浏览照片的程式
程式中会大量的开启指定的图档然后显示到视窗中
但每次读取到一定的量后,程式就会没办法再读取图片
严重甚至崩溃,检查后才发现似乎跟程式使用的内存有关
每当我程式读取的图片占用的内存到了1.2G以上,
程式很容易就无法再读取图片了,
我很确定我电脑的内存还有很多尚未使用的部分@@
我电脑有16G的内存,作业系统是WIN7 64位元
我用工作管理员看效能那一栏下面的实体内存部分有四个内容
分别是‘总共、快取的、可用、未使用’
根据我GOOGLE查到的结果,‘未使用’其实只是还没被作业系统移到‘快取的’而已
电脑闲置的时间越久,未使用就会越少,快取的就会越多,
这样电脑中的程式要用到内存时就可以迅速的从‘快取的’取出来使用,
我打开电脑的VM ware时,‘快取的’的确会大量的减少
但我发现我程式每次在读取图片时,‘快取的’都不会减少,
反而减少的都是‘未使用’
当下一张读取的图片档案大小超过‘未使用’时,程式就没办法读取照片了@@
而刚好我电脑的‘未使用’每次都差不多是剩1.1G左右
我不知道这段叙述跟我遇到的问题有没有相关ˇ_ˇ
我也不敢100%确定我这段叙述真的是正确的
所以想请问该怎么样才可以让程式读取更多的照片?
或者是说使用更多的内存
这问题我真的查了很久都查不太到解答...
本来有查到说有人讲我应该要用64位元的编译器才行,
但我在想这样32位元的系统不就不能执行了吗?
而且有很多32位元的程式都会超过2G以上的不是吗@@
不晓得有没有高手可以指点一下的,拜托了
我写了一个测试的读档程式放上来,不知道这样有没有违规,
有的话麻烦告知,我会速删的。
这程式会读取同资料夹下11.7MB的1.jpg图档,按一次按钮会读取五次
因为没有写执行绪,所以读取过程会delay一段时间,
想说可以测试看看是不是真的‘未使用’的部分不够大时程式就无法读取了。
https://mega.co.nz/#!UBsnCBSZ!hsvJ1ru5uU8KhL8zGoqsYww_3cINiUjK4Q3AAUzYQj0
不过写了这程式反而让我发现其他事情,
明明照片才11.7MB,可是开启一次却会让程式占用大约370M的内存
所以我自己的电脑只能开到三张,就没办法再开了
照片的大小是16744*5615,我把他相乘后再*4就是376M,
难道程式读取照片占用的内存是看这个@@?
我一直以为是看档案大小,虽然发现这事情,不过问题还是存在ˇ_ˇ
拜托各位指点一下了,谢谢
作者: LPH66 (-6.2598534e+18f)   2014-05-21 02:37:00
看这描述似乎是 memory leak...
作者: azureblaze (AzureBlaze)   2014-05-21 08:28:00
11.7MB是有压缩的的结果 要显示一定要解压缩所以用掉376M是正确的
作者: chchwy (mat)   2014-05-21 08:34:00
32bit程式不能用超过2G的内存,这是 Windows 的规定
作者: azureblaze (AzureBlaze)   2014-05-21 08:51:00
然后"剩下800M"和 "还有一块完整超过376M"是两回事
作者: a27417332 (等号卡比)   2014-05-21 09:08:00
然后工作管理员看到的和指标寻址空间也是两回事吧
作者: Chikei ( )   2014-05-21 12:30:00
http://goo.gl/S7UyqW OS限制就在那边,你还是把问题描述清楚(像是为何不释放?)让大家帮你想想合理的设计吧。
作者: pcyu16 (._.?)   2014-05-21 12:39:00
硬件跟OS 对程式来说都算先天限制吧..不管是什么接口 应该都没必要同时存这么多图片在内存?还有就是这只程式如果有现在以外的机器要用 怎么办...?
作者: blackwindy (黑色的风)   2014-05-21 13:11:00
你OS没修好
作者: donkeychen (Bad_To_The_Bone)   2014-05-21 14:34:00
(本人对影像处理不太熟) 不知道有没有相关http://goo.gl/loNDmg 也可能无关啦 毕竟我也不熟那个转换好像是在影像处理时用的 对于不处理储存是否能节省空间使用我不太知道 给个参考 希望有帮助
楼主: googled (15357)   2014-05-21 17:44:00
查了一下影像处理的效率,似乎转成char好像比较快@@来写个测试的程式看看
作者: LiloHuang (十年一刻)   2014-05-21 18:20:00
处理图片的双重循环,请先跑 height 再跑 width 会较佳如果要更快可以每次处理 32bit,或者用 SIMD Intrinsic另外之前有贴过的连结,我再分享一次给你参考观察内存用量请用 procexp.exe http://goo.gl/n7utTE搭配下 debug break point 来帮助自己厘清哪些阶段增加真正要快就是用 OpenCL 或者 CUDA 来跑你的算法CPU 跟 GPU 的差异 http://youtu.be/-P28LKWTzrI这就是 row major 读取的好处,跟先跑 height 目的一样假设你一个 pixel 就是 32bit 的话,每次就抓 32bitRGBA8888 转 BGRA8888,抓 32bit 后再用 bitwise 操作SIMD 操作使用 MMX (64bit), SSE (128bit) 的 CPU 指令让每次处理的资料量增加,请参考 http://goo.gl/KkIumm写 Intrinsic 的好处是,是指 #include <xmmintrin.h>来操作那些 SIMD 的指令,而不用自己写 inline assembly至于是不是要把资料从"空间域"转"频率域",要看问题类型影像处理有些细节要注意,row major 存取,内存对齐可以再上网多多查一些资料,大概如此。先跑 height 就是 row major 读取,资料就是这样摆放的这种存取方式可以有效的利用 cache,甚至做 prefetchOpenCV是个好选择,要快可再搭配 Intel IPP,加油囉 :D
作者: donkeychen (Bad_To_The_Bone)   2014-06-05 13:54:00
推LiloHuang大大 (y)

Links booklink

Contact Us: admin [ a t ] ucptt.com