Kotlin中Elvis运算符(空合并运算符)为何出现异常行为?
Kotlin 1.8.0中空合并链式调用的异常行为
问题描述
在selectedLanguage和configManager.get().agency均为null的场景下,两段逻辑看似一致的Kotlin代码表现完全不同:
异常代码(调用时返回null)
companion object { private const val DEFAULT_LANGUAGE_CODE = "en-us" } val currentLanguageCode: String get() { return selectedLanguage?.code ?: configManager.get().agency?.language ?: DEFAULT_LANGUAGE_CODE }
正常代码(调用时返回默认值"en-us")
val currentLanguageCode: String get() { val selectedCode = selectedLanguage?.code val configCode = configManager.get().agency?.language return selectedCode ?: configCode ?: DEFAULT_LANGUAGE_CODE }
反编译分析
我把两段代码转成字节码再反编译为Java,从结果看两段逻辑应该是等价的,但实际运行结果却不同:
正常代码反编译后的Java实现
// 正常工作版本 public final String getCurrentLanguageCode() { CommunityLanguage var10000 = this.selectedLanguage; String selectedCode = var10000 != null ? var10000.getCode() : null; ConfigAgency var3 = ((CaptureConfig)this.configManager.get()).getAgency(); String configCode = var3 != null ? var3.getLanguage() : null; String var4 = selectedCode; if (selectedCode == null) { var4 = configCode; } if (var4 == null) { var4 = "en-us"; } return var4; }
异常代码反编译后的Java实现
// 返回null的异常版本 public final String getCurrentLanguageCode() { String var1; label18: { CommunityLanguage var10000 = this.selectedLanguage; if (var10000 != null) { var1 = var10000.getCode(); if (var1 != null) { break label18; } } ConfigAgency var2 = ((CaptureConfig)this.configManager.get()).getAgency(); var1 = var2 != null ? var2.getLanguage() : null; } if (var1 == null) { var1 = "en-us"; } return var1; }
从反编译代码可以看到,异常版本最后同样有判断var1是否为null并赋值默认值的逻辑,但实际运行却返回了null,有没有人知道原因?
内容的提问来源于stack exchange,提问作者Matt Wolfe
相关产品推荐
相关产品推荐

