Kotlin系列五---数据类、密封类、内部类

概述:kotlin的学习已经有一段时间了,每天都会花一点时间简单看看,看过之后过不了多久就会忘记,再一次证明只是是需要整理的,本片我们就来整理一下基本的几个类的使用,比较简单大致都是和kotlin网站上的东西差不多。

数据类

无论在java还是其它语言中,为了代码逻辑的清晰,我们总会创建一些只用于保存状态属性或数据的类,这些类称之为数据类,在kotlin中为了更加简单和规范的使用数据类,为数据类加上了自己的标志和修饰词data,并有了自己的规则,那我们创建一个简单的数据类:
data class DataClass(var  name : String) {

}
为了确保生成的代码的一致性和有意义的行为,数据类必须满足以下要求:
  • 主构造函数需要至少有一个参数;
  • 主构造函数的所有参数需要标记为 val 或 var;
  • 数据类不能是抽象、开放、密封或者内部的;
  • (在1.1之前)数据类只能实现接口。
创建数据类的对象并获取其属性:
var data = DataClass("NAME")
println(data)
println(data.name)
打印属性结果:
02-07 09:50:05.995 3256-3256/? I/System.out: DataClass(name=NAME)
02-07 09:50:05.995 3256-3256/? I/System.out: NAME
kotlin为数据类的创建定义了一直的标准,那限制的标准一定是为了实现部分共有的功能,在创建每个数据类时,编译器自动从主构造函数中声明的所有属性导出以下成员:
  • equals()/hashCode() 对;
  • toString() 格式是 "DataClass(name=NAME)";
  • componentN() 函数 按声明顺序对应于所有属性;
  • copy() 函数
toString()方法就和上面输出data一样,属性的获取在上面也使用过,我们打印一下equals和hasCode方法:
Log.e("=====", data.hashCode().toString())
Log.e("=====", data.equals(data.copy(name = "Change")).toString())
这里我们单独介绍一次啊copy的属性,copy从字面上是复制某个属性,不过kotlin的复制是允许用户修改属性的,或者叫不完全意义上的复制,产生的是一个属性不一定相同的不同对象,其内部的方法可以描述为:
fun copy(name: String = this.name) =DataClass  (name)    
现在我们复制data对象,改变其名字:
println(data.copy(name = "Change"))
println(data)
输出结果:
02-07 10:01:04.454 4444-4444/? I/System.out: DataClass(name=Change)
02-07 10:01:04.454 4444-4444/? I/System.out: DataClass(name=NAME)
解构声明
解构声明:顾名思义分解构造函数的每个参数,而创建对象,上文中创建data是:var data = ....,现在使用解构函数创建
var (name) = DataClass("A")//这里的name直接可以使用
Log.e("======",name)
02-07 10:08:17.444 5393-5393/? E/======: A

密封类

密封类用来表示受限的类继承结构:当一个值为有限集中的类型、而不能有任何其他类型时。在某种意义上,他们是枚举类的扩展:枚举类型的值集合也是受限的,但每个枚举常量只存在一个实例,而密封类的一个子类可以有可包含状态的多个实例。
要声明一个密封类,需要在类名前面添加 sealed 修饰符。虽然密封类也可以有子类,但是所有子类都必须在与密封类自身相同的文件中声明。(在 Kotlin 1.1 之前, 该规则更加严格:子类必须嵌套在密封类声明的内部)。
创建密封类和其子类:
sealed class Parent

data class ChildFirst(var name: String) : Parent()

data class ChildSecond(var name: String):Parent()

data class ChildThird(var name: String):Parent()
  • 一个密封类是自身抽象的,它不能直接实例化并可以有抽象(abstract)成员。
  • 密封类不允许有非-private 构造函数(其构造函数默认为 private)。
  • 请注意,扩展密封类子类的类(间接继承者)可以放在任何位置,而无需在同一个文件中。
  • 使用密封类的关键好处在于使用 when 表达式 的时候,如果能够验证语句覆盖了所有情况,就不需要为该语句再添加一个 else 子句了。当然,这只有当你用 when 作为表达式(使用结果)而不是作为语句时才有用。
fun getName(parent: Parent) : String? = when (parent){
is ChildFirst -> parent.name
is ChildSecond -> parent.name
is ChildThird -> parent.name
}

内部类

kotlin中允许在一个类的内部嵌套一个类,不过此时的类不同于java中,两个类某种意义上的相互独立,内部的嵌套类无法使用外部的数据:
data class DataClass(var name: String) {
    
    class Data {
        fun print() {
            Log.e("===========", "DataClass.Data")
        }
    }

}

DataClass.Data().print()//02-07 10:23:40.106 6569-6569/? E/===========: DataClass.Data
此时的嵌套类虽然在一个累的内部,并不是嵌套类,因为kotlin中的内部类需要专有的修饰符:inner,现在我们修改上面的嵌套类:
var age: Int = 20

inner class Data {
     fun print() {
         Log.e("===========",age.toString())
     }
}
此时的调用方法也与之前的有所不同,要采用外部类的对象调用:
data.Data().print()
02-07 10:26:33.767 6909-6909/com.example.administrator.kotlinpractise E/===========: 20//输出外部类的数据
匿名内部类
使用对象表达式创建匿名内部类实例,我们对Rxjava的使用会比较多,我们就创建一个观察者的匿名对象:
Observable.just(1).subscribe(object : Observer<Int>{
    override fun onSubscribe(d: Disposable) {
        TODO("not implemented") //To change body of created functions use File | Settings | File Templates.
    }

    override fun onNext(t: Int) {
        TODO("not implemented") //To change body of created functions use File | Settings | File Templates.
    }

    override fun onComplete() {
        TODO("not implemented") //To change body of created functions use File | Settings | File Templates.
    }

    override fun onError(e: Throwable) {
        TODO("not implemented") //To change body of created functions use File | Settings | File Templates.
    }

})
使用object : T 创建T的匿名内部类,下面我们创建常用的设置点击事件的ClickListener:
air_view.setOnClickListener(object : View.OnClickListener{
    override fun onClick(v: View?) {
        println("Click")
    }

}
在kotlin中 如果对象是函数式 Java 接口(即具有单个抽象方法的 Java 接口)的实例, 你可以使用带接口类型前缀的lambda表达式创建它:
air_view.setOnClickListener{  println("Click")}
对这三个类的创建和使用就简单介绍到这里,只要知道其使用的形式和代表的意义,在使用中根据需要灵活运用即可。


猜你喜欢

转载自blog.csdn.net/alexwll/article/details/79277555