阅读人群:IOS开发新手
有时候didReceiveMemoryWarning不像女人的大姨妈来的那么确定,让人摸不着头脑,不过好在有Instruments这种神器,帮我们解决了不少问题。
用Instruments分析了一下刚做好的app,发现如果反复触发同一个页面(没有做缓存),内存居高不下,仔细搜索controller的类名,发现根本就没有释放掉,触发代码如下:
XXXViewController *viewController = [[XXXViewController alloc] init];
[self.navigationController pushViewController:viewController animated:YES];
释放代码如下:
[self.navigationController popViewControllerAnimated:YES];
这几行代码没有什么复杂的,为什么pop之后XXXViewController没有释放呢,刚开始以为是NavigationController本身的机制就是这样的,后来新建了工程,写了例子代码之后发现pop之后controller是确定能够释放的。
仔细用Instruments分析了一遍XXXViewController的retain和release历史,但由于经过ARC之后有大约70多条,一个一个的分析不知道能分析到什么时候,最后检查了一遍代码,发现是由于循环引用导致。
简单来说就是XXXViewController引用了SubViewController,而在初始化SubViewController的时候把self传给了SubViewController,而且是strong引用,结果就导致XXXViewController pop之后retainCount仍然为1,从而内存泄漏了。
相比较而言,java在循环引用上处理就比较给力,java的GC使用图算法从根对象出发,找到无法达到的对象:
而ARC只是编译时期的特性,在合适的地方插入retain和release代码,使用简单的对象引用计算来判断对象是否该释放。
怎么解决循环引用呢?大致有两种方法:
1、手动切断循环引用中的一端,比如在pop view的时候顺便把SubViewController对self的引用切断,置为nil
2、使用weak,弱引用,本例中,在SubViewController中对self的持有置为weak引用,表示不对retainCount加1,ARC遵循这样的原则:“只要某个对象被任一strong指针指向,那么它将不会被销毁。如果对象没有被任何strong指针指向,那么就将被销毁”。
大部分情况下,我们用不到weak引用,但它却时刻伴随着我们,一个常见的例子就是oc中常见的delegate设计模式,viewController中有一个strong指针指向它所负责管理的UITableView,而UITableView中的dataSource和delegate指针都是指向viewController的weak指针。
本例中引起循环引用的业务逻辑就是子controller要用到父controller的方法,这其实不用我们手工维持这么一个引用,可以使用self.parentViewController来获取,但在这之前你必须在addSubview的时候[self addChildViewController:subViewController],这是一个好习惯,参见:http://blog.devtang.com/blog/2012/02/06/new-methods-in-uiviewcontroller-of-ios5/
未优化时每触发一次都能泄漏0.5M,十次至少泄漏5M,优化后触发十次的内存:
基本上跟初始内存一模一样,可以断定没有任何泄漏了。
- 大小: 55.6 KB
- 大小: 226.8 KB
- 大小: 58.5 KB
- 大小: 38.7 KB
分享到:
相关推荐
内存泄漏是指程序在申请内存后,无法释放已申请的内存空间,一次小的内存泄漏可能不会立即引发问题,但随着时间推移,累积的内存泄漏会占用大量系统资源,导致应用性能下降。 在iOS中,自动引用计数(ARC,...
### iOS开发内存分配详解 #### 一、内存分配概述 在iOS开发中,理解内存管理是至关重要的。本文档将详细介绍iOS开发中的内存分配机制,包括不同区域的内存分配方式及其特点。 #### 二、虚拟内存与物理内存 在iOS...
内存泄漏是指程序在申请内存后,无法释放已申请的内存空间,一次小的内存泄漏可能不会立即引起问题,但随着时间的推移,累积的内存泄漏可能会导致应用程序占用的内存持续增长,直至耗尽系统资源,引发应用崩溃。...
在iOS开发中,内存泄漏是常见的问题之一,它会导致应用消耗过多内存,影响性能,甚至导致应用崩溃。本文将深入探讨“iOS内存泄漏调试工程”中的核心知识点,并以提供的AsyncImageTableviewDemo为例进行讲解。 1. **...
在iOS开发中,加载大图或过多图片可能会导致应用程序内存飙升,从而引发性能问题甚至App崩溃。本篇文章将深入探讨如何解决"ios加载图片内存暴涨"的问题,主要介绍三种策略:第一种是使用UIKit的`setImage`方法,第二...
内存泄漏是iOS开发中的一个常见问题,它会导致应用的可用内存逐渐减少,最终可能导致应用崩溃或系统资源耗尽。为了有效地识别和解决内存泄漏问题,iOS开发者可以利用Xcode自带的工具进行分析和调试。以下是两种查看...
首先,Instrument是iOS开发中的一个强大的工具,它可以用于检测应用程序的内存使用情况、性能瓶颈以及其他问题。通过监控Log日志,开发者可以发现内存消耗的峰值以及与之相关的代码行,以便进行优化。 在提供的部分...
根据提供的信息,我们可以推断出这是一本关于iOS开发进阶的书籍,作者为唐巧。虽然提供的部分内容似乎并不是实际的章节内容,但从标题、描述和标签中,我们可以推测本书可能涵盖的一些关键知识点。 ### iOS开发进阶...
《iOS开发指南(第5版)》是一本深入探讨iOS应用程序开发的专业书籍,旨在帮助开发者从零基础到熟练掌握Apple的移动操作系统上的应用构建过程。该书第五版更新了最新的开发技术和工具,确保读者能够使用最新的Xcode和...
#### 一、iOS开发概述 iOS开发是指为苹果公司的移动操作系统iOS创建应用程序的过程。iOS操作系统主要用于iPhone、iPad以及iPod Touch等设备。为了开发iOS应用,开发者通常会使用两种主流的编程语言:Swift和...
8. **内存泄漏检测**:内存泄漏是导致应用崩溃和性能下降的常见问题。插件可以帮助检测潜在的内存泄漏,开发者可以定位并修复那些没有正确释放的资源。 9. **多平台兼容性**:由于插件支持Android和iOS,这意味着它...
IOS 常见内存泄漏以及解决方案 IOS 是一个基于对象的操作系统,...内存泄漏是 IOS 开发中常见的问题,导致程序性能和稳定性下降。解决内存泄漏问题需要了解 IOS 的内存管理机制,并使用正确的编程技巧来避免内存泄漏。
在iOS开发中,内存管理是一个至关重要的环节,而OOM事件可能导致应用无响应甚至崩溃。Swift-OOMDetector能够实时监测应用的内存使用情况,当内存达到预设阈值时,会发出警告,从而帮助开发者及时发现可能导致OOM的...
《Xamarin iOS开发实战中册》是一本专为开发者准备的深入学习Xamarin技术,特别是针对iOS平台的应用开发指南。这本书旨在帮助读者掌握使用Xamarin工具集构建原生iOS应用程序的技能,从而实现跨平台的高效开发。...
在iOS开发中,应用程序的内存使用情况会直接影响到应用的运行效率和系统的整体性能。如果应用未能妥善管理内存,可能会导致内存泄漏、频繁的内存分配和释放,甚至应用崩溃等问题。因此,对iOS开发者而言,了解并正确...
"内存管理"是iOS开发的核心概念,它涉及到对象生命周期的管理,包括创建、持有和释放。了解何时和如何正确地释放内存可以防止内存泄漏,避免应用崩溃。"crash调试"这部分可能涉及如何识别和解决由于内存问题导致的...
书中会介绍如何有效地使用这些机制,避免内存泄漏和其他性能问题。 最后,测试和调试是开发过程中不可或缺的部分。Xcode作为Apple的官方集成开发环境,提供了强大的调试工具。书中可能会教你如何使用Xcode的断点、 ...
Instruments是Xcode内置的一款强大的性能分析工具,可以帮助开发者诊断内存泄漏、CPU使用率等问题。通过使用不同的模板(如Time Profiler、Leaks等),开发者可以深入了解应用的运行情况,并据此优化代码。 #### ...
《iOS开发进阶完整版 唐巧》是一份针对已具备基础iOS开发技能的开发者设计的高级教程,由知名iOS开发专家唐巧编写。这份资料深入探讨了iOS开发的各个方面,旨在帮助开发者提升技能,进一步提升其在iOS平台上的应用...
内存泄漏是iOS应用开发中常见的问题,如果不及时处理,可能导致应用耗尽系统资源,影响用户体验甚至导致应用崩溃。 1. **内存管理基础** 在理解MLeaksFinder之前,我们需要了解iOS中的内存管理机制。iOS使用ARC...