zl程序教程

您现在的位置是:首页 >  硬件

当前栏目

Instruments指南:如何调试内存泄露

内存调试 如何 指南 泄露
2023-09-14 08:58:20 时间

现在,你应该使用的ARC,而不是原来我们使用的MRC或者其他。但是我们在使用ARC的时候也会出现内存泄露的情况。
幸运的是,苹果为我们提供了Instruments,他可以用来检测你的应用程序的内存泄露。可能刚学习iOS开发的开发者被这个工具给吓到了,里面有太多东西了。其实他们是非常了不起的,而且也非常容易使用。
在这篇文章里,你将会通过使用XCode和Instruments来调试和发现内存相关的问题(例如内存泄露)。

我们这篇文章的目标就是用一个小demo应用程序检查和解决我们经常遇到的通常的内存相关的错误。demo下载地址:http://pan.baidu.com/s/1c0tvFGk (参考别人的,比较老)
打开Xcode,然后运行小demo,试着去点击几个cell,我们会发现它爆了,你得到的是一个可怕地EXC_BAD_ACCESS错误,调试器没有什么帮助去解决这个错误。
对于许多开发者来说这是很令人沮丧的。因为不清楚问题出在哪里。下面是给开发者的一些建议当你遇到EXC_BAD_ACCESS错误的时候:

设置Enable Zombie Objects参数,在可执行选项,这有时候有助于缩小问题原因。具体设置方法是点击运行右边的项目,然后选择Edit Scheme。在Run选项的Diagnositics中设置Enable Zombie Objects。然后Close。再次运行,可能会出现一些问题提示。 使用苹果的Instruments,例如Leaks来查看内存问题。 在你的代码中设置断点,然后一步一步执行直到接近crash的地方。 尝试注释掉相关的代码,然后直到它工作,然后回溯。

不幸的是,NSZombieEnabled选项没有对僵尸启示做任何事情,所以你可以抛弃这种方法了。当你使用ENable Zombie Objects时,我们再次运行APP,会发现有下列提示:

2015-08-08 21:37:28.657 PropMemFun[8190:3281809] *** -[CFString respondsToSelector:]: message sent to deallocated instance 0x7f8251c07890

这时候我们会定位到这句代码:

 NSString * message = [NSString stringWithFormat:@"Last sushi: %@. Cur sushi: %@", _lastSushiSelected, sushiString];

 

Bingo!这时候我们知道问题在这行,一个消息发送给了一个已经释放的string。这行使用了_lastSushiSelected和sushiString。此时sushiString是正常的因为我们在上边定义了。那么问题就可能出现在_lastSushiSelected上。因为sushiString是自动释放变量,所以_lastSushiSelected指向他的时候已经被释放了。因此添加

 _lastSushiSelected = [sushiString retain];

即可解决问题。再次运行发现问题解决。

Build,Analyze 和Recognize

没有了Crash我们现在看一下是否有内存泄露。通过Product-- Analyze,我们可以看到有两处内存泄露。分别在

return cell;

- (void)viewDidUnload {

 [_sushiTypes release];

 _sushiTypes = nil;

}
泄露和水管工(Leaks and Plumbers)

现在我们就使用Instruments。

第一步:首先我们打开Instruments。(按着control+空格键,输入instruments即可打开(也可以Product-- Profile打开)我这边测试用Product-- Profile打开不能定位带具体内存泄露代码)。 第二步:选择Leaks,然后Choose。 第三步:通过暂停右边的选择我们可以选择正在运行的程序。然后点击Record(红色圆圈按钮) 第四步:观察,我们可以发现在Leaks里面有一个红色圆柱,这说明了我们的APP存在内存泄露。 第五步:点击暂停,然后我们开始分析。
在Instruments下方的控制台中,我们把Leaks(如果是Allocation就点击选择Leaks)右边的选项Statistics选择为Call Trees。然后点击右边Call Tree设置,勾选Invert Call Tree 和Hide System Libraries。我们会发现显示出来的是一个消息名称。它将会带你到内存泄露的地方。双击那个消息即可。然后你就可以检查一下那里的代码,然后思考一下,你应该能发现和解决这个问题。然后解决过后重新运行Leaks去检测是否还会有内存泄露。

以上就是利用Instruments如何查找内存泄露。


1.INSTRUMENTS调试工具的使用(一)2.INSTRUMENTS调试工具的使用(二)3.INSTRUMENTS调试工具的使用(三)4.INSTRUMENTS调试工具的使用(四)5.
基于WinDbg的内存泄漏分析 在前面C++中基于Crt的内存泄漏检测一文中提到的方法已经可以解决我们的大部分内存泄露问题了,但是该方法是有前提的,那就是一定要有源代码,而且还只能是Debug版本调试模式下。实际上很多时候我们的程序会用到第三方没有源代码的模块,有些情况下我们甚至怀疑系统模块有内存泄露,但是有没有证据,我们该怎么办? 这时我们就要依靠无所不能的WinDbg了。
使用valgrind检查内存问题 作者:gfree.wind@gmail.com 博客:blog.focus-linux.net   linuxfocus.blog.chinaunix.net  本文的copyleft归gfree.wind@gmail.com所有,使用GPL发布,可以自由拷贝,转载。