Kotlin对象表达式属性作用域与遮蔽规则:代码为何输出0?
Kotlin代码输出0的原因及内部属性未遮蔽外部属性的解释
一、为什么代码输出0?
这段代码里,匿名对象的g()函数中直接调用println(x)时,编译器会优先解析外部f()函数作用域里的x(也就是值为0的那个局部变量),而不是匿名对象自身定义的val x = 1。
如果想要访问匿名对象自己的x,必须用this明确指代当前对象的成员:
fun g() { println(this.x) // 此时会输出1 }
二、为什么内部属性未遮蔽外部属性?
这是由Kotlin的词法作用域与成员访问规则决定的:
- 对于匿名对象的成员函数,当访问未加限定符的变量名时,编译器会按照局部变量→外部作用域变量→当前对象成员的顺序查找。外部
f()函数的x属于被捕获的外部作用域变量,优先级高于匿名对象的自身成员。 - 匿名对象的成员不会自动“遮蔽”外部同名变量,因为二者不属于同一查找层级——对象成员必须通过
this显式引用,才能覆盖外部变量的优先级。
对比普通类的情况:普通类的成员函数中直接写变量名,会优先查找类的成员;但匿名对象是特殊的嵌套作用域结构,外部作用域的局部变量会被优先解析,无需额外限定符。
内容的提问来源于stack exchange,提问作者Wickoo
相关产品推荐
相关产品推荐

