iOS中怎么判断可变和不可变的坑

  怎么判断NSString和NSMutableString呢

  看题

    BOOL result = [@"" isKindOfClass:[NSMutableString class]];
// A:YES B:NO

  送分题一看就选B的。然而正确答案却是A(这里提及下涉及的两个概念:类簇,工厂模式)

  看控制台弄出来的结果

    id str0 = [NSString alloc];//NSPlaceholderString->NSString
id str1 = [[NSString alloc] init];//__NSCFConstantString->__NSCFString->NSMutableString->NSString
id str3 = [NSString stringWithFormat:@""];//NSTaggedPointerString->NSString
id str4 = [NSMutableString alloc];//NSPlaceholderMutableString->NSMutableString->NSString
id str5 = [NSMutableString new];//__NSCFString->NSMutableString->NSString

  字符串常量,也就是str1那种创建方式得到的类型是__NSCFConstantString并且明目张胆的是NSMutableString的子类。无论如何请勇敢的质疑苹果脑残的设计。并且后面的Array和Dictionary就不存在这种脑残的地方。我们无法知道到底黑盒子里有多少这种子类,根据倒推法:

  所以现在判断一个字符串是可变的这么写就行了

BOOL isMutable = [str isMemberOfClass:NSClassFromString(@"__NSCFString")];//请注意是isMemberOfClass:这个方法不要用成isKindOfClass:

  把Array的控制台结果也弄出来简单的看一下

    NSArray* arr0 =        [[NSArray alloc] init];//__NSArray0->NSArray
NSArray* arr1 =        [NSArray arrayWithObject:@""];//__NSArrayI->NSArray
NSMutableArray* arr3 =   [[NSMutableArray alloc] init];//__NSArrayM->NSMutableArray->NSArray

  可以发现虽然NSArray也子嗣众多,但不会出现String那种近亲乱的情况。

  判断Array是不可变的这么写就行了,不需要写字符串的类型

BOOL notMutable = [arr isKindOfClass:[NSArray class]]&&![arr isKindOfClass:[NSMutableArray class]];

  NSDictionary的情况同NSArray。

  转注出:原文

===========更正===========================

上面的方法在实际使用中被证明是错的,看如下两个方法

//在有的版本中执行结果如下
@().description;//__NSCFString->NSMutableString->NSString
[NSString stringWithFormat:@"123%d",]//__NSCFString->NSMutableString->NSString

就是说这两种情况从外部审查类型来看,根本和[NSMutableString new]的效果是一样的,而且是响应下面的方法的

[xxx respondsToSelector:@selector(appendFormat:)];

但是实际的情况是一调用就崩溃了。不听老人言吃亏在眼前,真的是最打脸的道理最朴素。一个不开源的东西,我们就是喜欢在外面赌博。

思考了很久我发现了解决之道,大道果然至简:我不知道它怎么实现的,但是苹果知道……

所以:

    id copyed = [xxx copy];
if(copyed == xxx){
@"不可变".nslog();
}else{
@"可变的".nslog();
}

如果一个对象是可变的,copy之后会返回新对象,我们比较这两个指针就可以了。里面是如何实现的,我们不再关心。

iOS中怎么判断可变和不可变的坑(更正版)的更多相关文章

  1. iOS 中如何判断当前是2G/3G/4G/5G/WiFi

    5G 什么的,还得等苹果API更新啊,不过将来还是这个处理过程就是了. 关于判断当前的网络环境是2G/3G/4G,这个问题以前经常看到,最近在一工程里看到了如果判断的API.而在撸WebRTC音视频通 ...

  2. IOS中如何判断APP是否安装后首次运行或升级后首次运行

    对于是否为首次安装的App可以使用如下方法来判断 [[NSUserDefaults standardUserDefaults] boolForKey:@"firstLaunch"] ...

  3. ios中怎么样判断路径最后的后缀名称

    使用hasSuffix属性即可 例如 [photo.thumbnail_pic.lowercaseString hasSuffix:@"gif"]

  4. IOS 中runtime 不可变数组__NSArray0 和__NSArrayI

    IOS 中runtime 不可变数组__NSArray0 和__NSArrayI 大家可能都遇到过项目中不可变数组避免数组越界的处理:runtime,然而有时候并不能解决所有的问题,因为类簇不一样 # ...

  5. python中的可变与不可变对象

    Python中的可变对象和不可变对象 什么是可变/不可变对象 不可变对象,该对象所指向的内存中的值不能被改变.当改变某个变量时候,由于其所指的值不能被改变,相当于把原来的值复制一份后再改变,这会开辟一 ...

  6. Java中的String为什么是不可变的?

    转载:http://blog.csdn.net/zhangjg_blog/article/details/18319521 什么是不可变对象? 众所周知, 在Java中, String类是不可变的.那 ...

  7. php学习笔记5--php中的可变变量,可变函数及匿名函数

    可变变量指的是:将一个变量的值再次当做一个变量名从而得到另外一个变量的值.如:$name = 'dqrcsc';$myname = 'name'; //$myname的值碰巧是另一个变量的变量名ech ...

  8. Java基础知识强化101:Java 中的 String对象真的不可变吗 ?

    1. 什么是不可变对象?       众所周知, 在Java中, String类是不可变的.那么到底什么是不可变的对象呢? 可以这样认为:如果一个对象,在它创建完成之后,不能再改变它的状态,那么这个对 ...

  9. IOS开发中如何判断程序第一次启动(根据判断结果决定是否显示新手操作引导)

    IOS开发中如何判断程序第一次启动 在软件下载安装完成后,第一次启动往往需要显示一个新手操作引导,来告诉用户怎么操作这个app,这就需要在程序一开始运行就判断程序是否第一次启动,如果是,则显示新手操作 ...

随机推荐

  1. jQuery的attr()与prop()的区别

    jQuery的attr()与prop()都是用于获取与设置属性的,但它们又各有不同. attr()一般是用于设置默认值,prop()一般是用于设置属性值,即对于像“diabled”,"che ...

  2. 【Yii系列】错误处理和日志系统

    缘起 跟随上一章的脚步,上一章中,我们主要讲解了在用户发起请求,解析请求,服务器反馈请求以及session的一些知识点,这过程中,难免会遇到一些问题,比方说数据库查询失败,用户输入导致脚本出错,网络问 ...

  3. vs 编译error1083

    1)右键查看该项目的属性 2)点击配置属性——〉  C/C++  ——〉  常规  ——〉 附加包含目录——〉将报错文件所在目录添加进去 3) 将项目的本地路径替换为工程相对路径 一般来说,打不开文件 ...

  4. Python初学者第十八天 函数(2)

    18day 函数 1.函数的返回值:return a.函数外的代码想要获取函数的返回结果时,即可使用return语句 b.函数中如遇到return后,会停止执行,并返回结果.所以若函数未使用retur ...

  5. Python学习---抽屉框架分析[点赞功能/文件上传分析]0317

    点赞功能分析 前台传递过来新闻id[new_id]和session[session内有用户ID和用户之间的信息]到后台 后台News数据库内用户和新闻是多对多的关系,查看第三张表中的内容,判读用户Id ...

  6. July 27th 2017 Week 30th Thursday

    A smile is the most charming part of a person forever. 微笑永远是一个人身上最好看的东西. Smile in the mirror, and yo ...

  7. 20、资源与本地化 System.Resources

    可以将字符串.图像或对象数据等资源包含在资源文件中,方便应用程序使用. .NET Framework 提供了五种创建资源文件的方法: •创建一个包含字符串资源的文本文件.或创建一个包含字符串.图像或对 ...

  8. 异步模式:Callbacks, Promises & Async/Await

    [译]异步JavaScript的演变史:从回调到Promises再到Async/Await https://www.i-programmer.info/programming/theory/8864- ...

  9. BZOJ3926:[ZJOI2015]诸神眷顾的幻想乡(广义SAM)

    Description 幽香是全幻想乡里最受人欢迎的萌妹子,这天,是幽香的2600岁生日,无数幽香的粉丝到了幽香家门前的太阳花田上来为幽香庆祝生日. 粉丝们非常热情,自发组织表演了一系列节目给幽香看. ...

  10. POJ3384 Feng Shui

    嘟嘟嘟 昨天我看到的这道题,今天终于A了. 写这道题的时间其实并不长,主要是我为这题现学了一个半平面相交(虽然是\(O(n ^ 2)\)的--) 思路说难也不难,关键是第一步的转化得想到. 首先可以肯 ...