iOS 开发遇到的问题之(nil指针对NSDictionary及NSArray初始化的影响)
nil指针对NSDictionary及NSArray初始化的影响
最近在做项目的时候遇到一个挺坑的崩溃问题,是由于NSDictionary初始化时nil指针引起的崩溃。假设我们现在要初始化一个{key1 : value1, key2 : value2, key3 : value3}的NSDictionary,一般有两种初始化方法:
1、使用标准的初始化方法:
NSDictionary *dictionary =[[NSDictionaryalloc] initWithObjectsAndKeys:value1,@"key1",value2,@"key2", value3 ,@"value3",nil];
2、使用ios6.0以后新支持的初始化方法:
NSDictionary *dictionary =@{@"key1" : value1,@"key2" : value2,@"key3" : value3};
现在我们对value1 value2 value3进行赋值,并把value2设为nil指针:
NSString *value1 =@"value1";NSString *value2 =nil;NSString *value3 =@"value3";
这时如果使用第二种初始化方法,运行程序会发现崩溃,日志如下:
DictionaryTextDemo[29390:1329578] Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: ' -[__NSPlaceholderDictionary initWithObjects:forKeys:count:]: attempt to insert nil object from objects[1]'
发现系统会阻止你向object[1]插入一个nil指针,查询苹果官方文档得到
Discussion
This method steps through the objects andkeys arrays, creating entries in the new dictionary as it goes. AnNSInvalidArgumentException is raised if a key or value object isnil.
也就是说使用这种初始化方法的时候必须保证key跟value都不为nil,因此我们需要在初始化之前对其进行判断,如果为nil就不加入字典。但是如果有需求让value必须为空的时候,可以将value赋值为[NSNull null]这样就可以成功插入字典,最后打印出来的结果是
DictionaryTextDemo[29510:1338517] dictionary : {key1 = value1;key2 = "";value3 = value3;}
另一种解决方法就是使用标准的初始化方法,即第一种初始化方法。但同时也要注意一个问题,使用
NDictionary *dictionary = [[NSDictionaryalloc]initWithObjectsAndKeys:value1,@"key1",value2,@"key2", value3 ,@"value3",nil];
如果我们把其中一个key或者value设为nil指针,那么系统会判断为全部对象插入完成,即相当于我们初始化数组及字典时最后的nil。因此这种方法虽然能避免插入nil指针时抛出的异常,但可能会成为一个工程中很大的安全隐患,并且难以发现。所以推荐使用第二种初始化方法,并对nil指针进行必要的判断,选择性使用[NSNull null]来实现特点的需求。同理,使用NSArray时也应该注意这类问题。
思考:想使用 {key1:value1,key2 "",key3:value3} 但是要判断没个value 不能为nil;相当麻烦。而使用,initWithObjectsAndKeys:value1;不会崩溃,但是 系统会认为是末尾的nil,造成参数不完整。调试时难以发现。
1.注意对变量初始化。
2.赋值操作时,对=号后面的对象判断。
其实想写个类别是想实现,对nil 校验,nil 自动转换为@“”;还没想好!
更新:2016-09-30
在swift 3.0 中可以存储nil 对象。不会再崩溃了。很好的完善。
iOS 开发遇到的问题之(nil指针对NSDictionary及NSArray初始化的影响)的更多相关文章
- iOS 开发设计常用软件及工具整理
1, xCode 2, AppCode 3, Skech 原型设计软件 4, Hype 动画设计工具 5, fontawsome 免费图表 6, Prepo icon, images.catlog 生 ...
- iOS开发系列--打造自己的“美图秀秀”
--绘图与滤镜全面解析 概述 在iOS中可以很容易的开发出绚丽的界面效果,一方面得益于成功系统的设计,另一方面得益于它强大的开发框架.今天我们将围绕iOS中两大图形.图像绘图框架进行介绍:Quartz ...
- iOS开发系列--通讯录、蓝牙、内购、GameCenter、iCloud、Passbook系统服务开发汇总
--系统应用与系统服务 iOS开发过程中有时候难免会使用iOS内置的一些应用软件和服务,例如QQ通讯录.微信电话本会使用iOS的通讯录,一些第三方软件会在应用内发送短信等.今天将和大家一起学习如何使用 ...
- iOS开发系列--数据存取
概览 在iOS开发中数据存储的方式可以归纳为两类:一类是存储为文件,另一类是存储到数据库.例如前面IOS开发系列-Objective-C之Foundation框架的文章中提到归档.plist文件存储, ...
- iOS开发系列--无限循环的图片浏览器
--UIKit之UIScrollView 概述 UIKit框架中有大量的控件供开发者使用,在iOS开发中不仅可以直接使用这些控件还可以在这些控件的基础上进行扩展打造自己的控件.在这个系列中如果每个控件 ...
- 转载:iOS开发之让你的应用“动”起来
在iOS中随处都可以看到绚丽的动画效果,实现这些动画的过程并不复杂,今天将带大家一窥iOS动画全貌.在这里你可以看到iOS中如何使用图层精简非交互式绘图,如何通过核心动画创建基础动画.关键帧动画.动画 ...
- iOS开发系列—Objective-C之Foundation框架
概述 我们前面的章节中就一直新建Cocoa Class,那么Cocoa到底是什么,它和我们前面以及后面要讲的内容到底有什么关系呢?Objective-C开发中经常用到NSObject,那么这个对象到底 ...
- iOS开发系列--IOS程序开发概览
概览 终于到了真正接触IOS应用程序的时刻了,之前我们花了很多时间去讨论C语言.ObjC等知识,对于很多朋友而言开发IOS第一天就想直接看到成果,看到可以运行的IOS程序.但是这里我想强调一下,前面的 ...
- iOS开发系列--让你的应用“动”起来
--iOS核心动画 概览 在iOS中随处都可以看到绚丽的动画效果,实现这些动画的过程并不复杂,今天将带大家一窥iOS动画全貌.在这里你可以看到iOS中如何使用图层精简非交互式绘图,如何通过核心动画创建 ...
随机推荐
- Apache与Tomcat的整合
一 Apache与Tomcat比较联系 apache支持静态页,tomcat支持动态的,比如servlet等. 一般使用apache+tomcat的话,apache只是作为一个转发,对jsp的处理是由 ...
- BZOJ1095 [ZJOI2007]Hide 捉迷藏
动态树分治,用三个set分别维护每个重心到每一个子树的距离种类.每个重心所有子树的最大值和次大值.全局答案的最大值.复杂度O(nlogn^2) 代码 #include<cstdio> #i ...
- Android中处理崩溃异常和记录日志
大家都知道,现在安装Android系统的手机版本和设备千差万别,在模拟器上运行良好的程序安装到某款手机上说不定就出现崩溃的现象,开发者个人不可能购买所有设备逐个调试,所以在程序发布出去之后,如果出现了 ...
- nginx,控浏览器缓存,前端优化方案
1,困惑 做web项目,对于开发者来说,一个最头痛的问题就是浏览器缓存,有缓存,js更改了,html更改了,发布服务器以后用户往往无法通过浏览器访问到最新的类容,需要用户主动去刷新页面, 因为一直做企 ...
- Web 2D/3d
首选应该是H5,通过现成的js库来实现,兼容性应该不错 其次可以考虑使用Unity3d,开发起来应该比较快 搜集点资料先放起来~ Unity3d: http://unity3d.com/cn/get- ...
- 【转】PowerShell入门(十):使用配置文件
转至:http://www.cnblogs.com/ceachy/archive/2013/03/01/PowerShell_Profile.html 在命令行中定义别名.变量和函数,只是将它们添加在 ...
- 敏捷开发之Scrum扫盲篇
现在敏捷开发是越来越火了,人人都在谈敏捷,人人都在学习Scrum和XP... 为了不落后他人,于是我也开始学习Scrum,今天主要是对我最近阅读的相关资料,根据自己的理解,用自己的话来讲述Scrum中 ...
- Canny边缘检测
1.Canny边缘检测基本原理 (1)图象边缘检测必须满足两个条件:一能有效地抑制噪声:二必须尽量精确确定边缘的位置. (2)根据对信噪比与定位乘积进行测度,得到最优化逼近算子.这 ...
- 浮点型数据运算精度bug
/** * 校验是否为数字 * @param arg * @return */ function checkIsNumber(arg){ if(arg != null && arg.t ...
- 瘋耔java语言笔记
一◐ java概述 1.1 ...