三目运算符(var ? var : @"") OR (a ?:

2021-01-19  本文已影响0人  山已几孑

好吧,先说最终结论,没有最终结论,我也不知道用啥。

这两个都是三目运算符,在我们给属性或者参数设置非空数据时十分常用,然后,我就十分好奇到底用哪种写法更好(其实我喜欢第二种,更简洁,跟swift ?? 更像,也好理解),
但是吧,感觉不行啊,得有证据,所以简单编写了一个测试代码,并用objdump把中间文件给打印了一下,

代码简单的不要不要的:

-(void)functionOne {
    NSString * a = @"";
    NSString * b = a ? a : @"";
}
-(void)functionTwo {
    NSString * a = @"";
    NSString * b = a ?: @"";
}

中间文件(.o)的位置在/Users/UName/Library/Developer/Xcode/DerivedData/$PROJECTNAME-RandomString/Build/Intermediates.noindex/$PROJECTNAME.build/Debug-iphonesimulator/$PROJECTNAME.build/Objects-normal/x86_64 里面的$PROJECTNAME的位置自己替换
中间文件如下图.0文件

image.png

然后再终端敲kyang@Kyang-3 x86_64 % objdump -S -g DumpTest.o就把编译后的文件打印出来了。

这边就不贴代码了,直接贴个图
简单分析一下就看到 ?:的方式比 ? : 的方式要多了两行指令,说明它并不能直接理解 ?: 这种形式,而是对它做了一定的转换,比直接对比,多了两条指令。

汇编指令对比

是不是就说明 ?:? :要慢????
不过吧,现在cpu都这么屌,这两条肯定不算事儿了,具体用哪个大家还是看个人喜好吧。PS:怎么办,想建议别人换成?:😶😶😶,别急!!!

然后我们换个稍微复杂点的例子,真的是稍微复杂点

-(void)functionOne {
    NSString * b = [self randomString] ? [self randomString] : @"";
}
-(void)functionTwo {
    NSString * b = [self randomString] ?: @"";
}
-(NSString * __nullable)randomString {
    if (arc4random() % 2) {return @"a";}
    return nil;
}

然后重复上面的操作,得到两个方法的汇编指令的对比:


一屏装不下啊,拖了拖

可以看到,指令不止多了一点半点,区别还是很大的,这次,反而是 ?: y以大优势反超。
其实也好理解:

    NSString * b = [self randomString] ? [self randomString] : @"";
    /*
     1. 执行[self randomString]
     2. 判断返回值是不是为空
     3. 如果不为空那么
     4. 继续执行[self randomString]
     5. 返回值赋值给b
     */

    NSString * b = [self randomString] ?: @"";
    /*
     1. 执行[self randomString]
     2. 判断返回值是不是为空
     3. 如果不为空那么 下一步
     4. 返回值赋值给b
     */

第二种方式少执行了一个方法,这里仅仅是一个if else,但如果是是一个其他的方法,比如富文本之类的,差距只会是更大!!

可以给一个不严谨的结论了:

上一篇 下一篇

猜你喜欢

热点阅读