🔥码云GVP开源项目 12k star Uniapp+ElementUI 功能强大 支持多语言、二开方便! 广告
#### **可空性的实现原理** ~~~ /** * 研究可空性的实现原理 */ fun main(args: Array<String>) { } fun testNullable1(x:String,y:String?):Int{ return x.length } fun testNullable2(x:String,y: String?):Int?{ return y?.length } fun testNullbale3(x: String,y: String?):Int?{ return y!!.length } ~~~ 打开IDEA的 Tools > Kotlin > Show Kotlin Bytecode,然后,点击 Decompile , 我们可以得到反编译的Java代码 ~~~ package A基础; import kotlin.Metadata; import kotlin.jvm.internal.Intrinsics; import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; @Metadata( mv = {1, 1, 13}, bv = {1, 0, 3}, k = 2, d1 = {"\u0000\u001c\n\u0000\n\u0002\u0010\u0002\n\u0000\n\u0002\u0010\u0011\n\u0002\u0010\u000e\n\u0002\b\u0002\n\u0002\u0010\b\n\u0002\b\u0006\u001a\u0019\u0010\u0000\u001a\u00020\u00012\f\u0010\u0002\u001a\b\u0012\u0004\u0012\u00020\u00040\u0003¢\u0006\u0002\u0010\u0005\u001a\u0018\u0010\u0006\u001a\u00020\u00072\u0006\u0010\b\u001a\u00020\u00042\b\u0010\t\u001a\u0004\u0018\u00010\u0004\u001a\u001f\u0010\n\u001a\u0004\u0018\u00010\u00072\u0006\u0010\b\u001a\u00020\u00042\b\u0010\t\u001a\u0004\u0018\u00010\u0004¢\u0006\u0002\u0010\u000b\u001a\u001f\u0010\f\u001a\u0004\u0018\u00010\u00072\u0006\u0010\b\u001a\u00020\u00042\b\u0010\t\u001a\u0004\u0018\u00010\u0004¢\u0006\u0002\u0010\u000b¨\u0006\r"}, d2 = {"main", "", "args", "", "", "([Ljava/lang/String;)V", "testNullable1", "", "x", "y", "testNullable2", "(Ljava/lang/String;Ljava/lang/String;)Ljava/lang/Integer;", "testNullbale3", "helloKotlin"} ) public final class NullableTypesKt { public static final void main(@NotNull String[] args) { Intrinsics.checkParameterIsNotNull(args, "args"); } public static final int testNullable1(@NotNull String x, @Nullable String y) { Intrinsics.checkParameterIsNotNull(x, "x"); return x.length(); } @Nullable public static final Integer testNullable2(@NotNull String x, @Nullable String y) { Intrinsics.checkParameterIsNotNull(x, "x"); return y != null ? y.length() : null; } @Nullable public static final Integer testNullbale3(@NotNull String x, @Nullable String y) { Intrinsics.checkParameterIsNotNull(x, "x"); if (y == null) { Intrinsics.throwNpe(); } return y.length(); } } ~~~ 在不可空变量调用函数之前,都检查了是否为空, 使用的是 kotlin.jvm.internal.Intrinsics 这个Java类里面的checkParameterIsNotNull 方法。如果是 null 就抛出异常: ~~~ public static void checkParameterIsNotNull(Object value, String paramName) { if (value == null) { throwParameterIsNullException(paramName); } } ~~~ 同时,我们可以看出在Kotlin中函数的入参声明 ``` fun testNullable1(x: String, y: String?) ``` 反编译成等价的Java代码是 ~~~ public static final int testNullable1(@NotNull String x, @Nullable String y) ~~~ 可以看出,这里**使用注解 @NotNull 标注不可空的变量,使用注解 @Nullable 标注一个变量可空**。 可空变量的安全调用符 y?.length 等价的Java代码就是 ~~~ y != null ? y.length() : null; ~~~ 可空变量的断言调用 y!!.length 等价的Java代码是: ~~~ if (y == null) { Intrinsics.throwNpe(); } return y.length(); ~~~