文章19 | 阅读 9942 | 点赞0
对于Backing Field这个概念,在Java中是没有的,是Kotlin中新引入的概念。我们先来看看它在什么情况下使用:
class Person {
var username: String = "hello"
get() {
println("getter invoked...")
return field
}
set(value) {
println("setter invoked...")
field = value
}
}
要想理解Backing Field,首先要明确一点:在Java中,通常将域(成员变量,Field)和它的访问器(Setter/Getter)联合起来称作是属性(Property);但是在Kotlin中,属性是作为一级语言特征,完全替代域和访问器的概念。
举个例子,我们定义一个类:
class User(val name: String, var age: Int)
然后我们在main函数中使用它:
fun main(args: Array<String>){
val user = User(“zhangsan”, 25)
println(user.name)
user.age = 29
println(user.age)
}
可以看出,无论是获取还是改变这个User里的age,从字面上看来都是age这个属性,都是它本身,是把它当做是不可分割的整体。而在Java中,要想实现前面的一样的效果,是需要有三部分:首先你得声明一个成员变量(域),然后为其生成对应的set、get方法才能实现读取和更新的功能。
明确了这两点之后,Backing Field的作用就可以体现了,类比到Java上,就是你声明的那个成员变量,是真正存储属性值的地方。
###2018.12.11更新###
明确了这两点之后呢,实际上我们可以发现,在使用属性的地方是不需要关注这个Backing Field的:像user.age = 29这种,这个时候就会触发age的set()方法的调用;像println(user.age)这行代码一样,这个时候就会触发name的get()方法的调用。无论set还是get,我们都是使用这种形式user.age。正如前面所说的,Kotlin中属性是作为一级语言特性的,属性包含了域、set和get方法三个部分,对于使用者来说是很方便的。而我们在需要自定义get、set方法时,我们又是需要区分这三者的,就拿set方法来说:如果这个地方你不知道field字段(也就是Backing-field),你不写成field = value,那你会怎么写?那只能写成这样:
注意左边红框中这个标识,在IDEA里面就表示递归调用了。如果在写这样的main函数进行测试的话:
最终肯定会内存溢出的。
所以,backing field代表的就是原来Java中的那个实际存储数据的成员变量!
版权说明 : 本文为转载文章, 版权归原作者所有 版权申明
原文链接 : https://blog.csdn.net/xlh1191860939/article/details/81983104
内容来源于网络,如有侵权,请联系作者删除!