Kotlin学习(四)—— 类和对象,继承,覆盖,抽象类,属性和字段,接口,可见性修饰符,扩展-阿里云开发者社区

开发者社区> 刘桂林> 正文

Kotlin学习(四)—— 类和对象,继承,覆盖,抽象类,属性和字段,接口,可见性修饰符,扩展

简介: 一.类和对象 1. 类 Kotlin和java的类的声明都是一样的,用class表示,比如 class TestClass { } 如果是空类的话,大括号都可以省了 2.
+关注继续查看

一.类和对象

1. 类

Kotlin和java的类的声明都是一样的,用class表示,比如

class TestClass {

}

如果是空类的话,大括号都可以省了

2.构造函数

一个主构造函数和多个次要函数,主函数在类名后,如

class TestClass {
    //主函数
    class TestClass constructor(firstName: String) {
        init {
            print("这里初始化")
        }
    }
}

如果主构造函数没有任何注解或者可⻅性修饰符,可以省略这个 constructor 关键字。
并且主构造函数不允许任何代码,初始化的代码可以放在init块中

我们再来看下次构造函数

类也可以声明前缀有 constructor的次构造函数:

class Person {
        constructor(parent: Person) {
        parent.children.add(this)
    }
}

3.实例化类对象

Kotlin中没有new,所以直接调用

class TestClass {
    //主函数
    class TestClass constructor(firstName: String) {
        init {
            print("这里初始化")
        }
    }
    constructor(firstName: String) {
        print("次构造函数")
    }
}

class Test{

    //实例化类对象
    val test = TestClass("lgl");
}

二.继承

所有的类都有一个超类Any,有点类似于JAVA中的Object,但是他们确是不同的,只是概念相似而已,因为Any只有有数的几个方法

这里我们定义一个基类BaseClass

 open class BaseClass {
     class BaseClass constructor(str:String){

     }
 }

这里的open,是公开的意思,和JAVA中的final完全相反

那我们再定义一个类去继承基类

class SonClass : BaseClass(){

}

当然,括号都是可以取消的

如果类没有主构造函数,那么每个次构造函数必须使⽤ super 关键字初始化其基类型,比如我们Android中的使用

class MyView : View {
    constructor(ctx: Context) : super(ctx)
    constructor(ctx: Context, attrs: AttributeSet) : super(ctx, attrs)
}

三.覆盖

这个很好理解,有继承就可以覆盖,我们来看一段代码

open class Base {
    open fun v() {
        print("Base...")
    }
    fun nv() {}
}

class Son() : Base() {
    override fun v() {
        print("Son...")
    }
}

fun main(args: Array<String>) {
    val son = Son();
    son.v()
}

这里有一个被open修饰的Base,里面有个Base方法,里面有打印,我现在有一个Son类,继承Base,并且override修饰重写v方法,再打印,那我的main方法,实例化这个对象后调用,打印的就是Son…了

这里写图片描述

标记为 override 的成员本⾝是开放的,也就是说,它可以在子类中覆盖,如果不想再次被覆盖,可以再修饰一个final

上面提到的是方法的覆盖,我们还可以覆盖属性,但是也是同样的,需要override修饰,比如


open class Base {

    open var a = 9;

    open fun v() {
        print("Base...")
    }

    fun nv() {}
}

class Son() : Base() {

    override var a = 8;

    override fun v() {
        print("Son...")
    }
}

fun main(args: Array<String>) {
    val son = Son();
    son.v()
    print(son.a)
}

在这段代码中,我们可以看到在基类中定义了一个属性a,然后子类中覆盖了一个a,输出的就是子类的a值了

如果我们想用到父类的方法,可以使用super

class Son() : Base() {

    override var a = 8;

    override fun v() {
        super.v()
        print("Son...")
    }
}

如果你是砸死内部类中想使用,那么需要super@Son.v()

在 Kotlin 中,实现继承由下述规则规定:如果⼀个类从它的直接超类继承相同成员的多个实现,它必须覆盖这个成员并提供其⾃⼰的实现(也许⽤继承来
的其中之⼀)。为了表⽰采⽤从哪个超类型继承的实现,我们使⽤由尖括号中超类型名限定的 super,如 super :

open class A {
    open fun f() { print("A") }
    fun a() { print("a") }
}
interface B {
    fun f() { print("B") } // 接⼝成员默认就是“open”的
    fun b() { print("b") }
}
class C() : A(), B {
    // 编译器要求覆盖 f():
    override fun f() {
        super<A>.f() // 调⽤ A.f()
        super<B>.f() // 调⽤ B.f()
    }
}

四.抽象类

abstract class Impl{
    abstract open fun f()
}

class Impl1():Impl(){

    override fun f() {

    }
}

这里的open可以不声明,并且我们可以一个抽象成员覆盖一个非抽象的开放成员,如例子

    open class Base {
        open fun f() {}
    }
    abstract class Derived : Base() {
        override abstract fun f()
    }

五.属性和字段

我相信大家对属性应该是比较了解的,我们在第二篇的时候也已经说过

class H {
    var a: String = "Hello"
    var b: Int = 0
    var c: Boolean = true;
}

想要调用的话

fun main(args: Array<String>) {
    val h = H();
    print("a:${h.a}b:${h.b}c:${h.c}")
}

在kt中,get和set就比较有意思了,正确的语法是:

var <propertyName>[: <PropertyType>] [= <property_initializer>]
    [<getter>]
    [<setter>]

如下代码

class H {
    var a: String
        get() = this.toString()
        set(value) {
            a == value
        }
    var b: Int = 0
    val c: Boolean = true
}

我就定义了a的get和set

六.接口

kt的接口的关键字interface,比如

interface Impl {
    fun A()
    fun B() {
        //可选方法体
    }
}

如果你想实现一个接口,你可以

class Tests : Impl {

    override fun A() {

    }
    //B方法可以不需要实现
}

你也可以在接口中定义一些属性,但是必须是抽象的或者对外提供访问的

interface Impl {

    //抽象
    val a: String
    val b: String
        get() = "Hello"

    fun A()
    fun B() {
        //可选方法体
    }
}

class Tests() : Impl {

    override val a: String = "Hello"

    override fun A() {

    }
    //B方法可以不需要实现
}

七.可见性修饰符

kt中有四种可见性修饰符,private 、protected 、internal 和 public,默认是public

  • public 随处可见

  • private 声明他的文件中可见

  • internal 相同模块可见

  • protected 不适用于顶层声明

这里还有一点需要注意的是,在JAVA中我们private中修饰的变量最终可以通过set/get的方式去访问,但是在kt中,外部类是不能访问内部类修饰的private成员

八.扩展

扩展,扩展一个类或者对象的新功能无需继承该类或使⽤像装饰者这样的任何类型的设计模式

声明一个扩展函数,我们需要一个接收者类型 也就是被扩展的类型来作为他的前缀,来看代码:

fun main(args: Array<String>) {
    val a = listOf<Int>()
    a.open(1, 2)
}

//扩展List一个open方法
fun List<Int>.open(a: Int, b: Int) {
    print(a + b)
}

这里就看的很清晰了,一个List本来没有open的方法,我通过扩展就给他加上了,并且内部实现了输出想加的结果
当然,我们并不会局限于哪些类型,所以通过泛型去装饰一下

//扩展List一个open方法
fun <T> List<T>.open(a: Int, b: Int) {
    print(a + b)
}

如果有兴趣的话,可以来Github参与一下

我的公众号,期待你的关注

版权声明:本文内容由阿里云实名注册用户自发贡献,版权归原作者所有,阿里云开发者社区不拥有其著作权,亦不承担相应法律责任。具体规则请查看《阿里云开发者社区用户服务协议》和《阿里云开发者社区知识产权保护指引》。如果您发现本社区中有涉嫌抄袭的内容,填写侵权投诉表单进行举报,一经查实,本社区将立刻删除涉嫌侵权内容。

相关文章
Go语言学习笔记(四)结构体struct & 接口Interface & 反射reflect
加 Golang学习 QQ群共同学习进步成家立业工作 ^-^ 群号:96933959 结构体struct struct 用来自定义复杂数据结构,可以包含多个字段(属性),可以嵌套; go中的struct类型理解为类,可以定义方法,和函数定义有些许区别; struct类型是值类型。
1183 0
ASP.NET Core教程【三】实体字段属性、链接标签、并发数据异常、文件上传及读取
前文索引:ASP.NET Core教程【二】从保存数据看Razor Page的特有属性与服务端验证ASP.NET Core教程【一】关于Razor Page的知识 实体字段属性 再来看看我们的实体类 public class Movie { public int...
1550 0
《Effective Objective-C 2.0》4、Objective-C类的属性
1、属性——property Objective-C的属性用于封装对象之中的数据,其作用同类的数据成员类似,但是所起到的作用远远大于普通的数据成员。
751 0
分割工具——按字段属性
在以前的文章ArcGIS按字段属性分割文件 中写到如何通过ArcGIS或FME来按字段属性表中字段来分割文件,甚至有网友还写出了模型文件。今天用了分割工具才恍然大悟,原来ESRI早就做好了这个工具。 如果要按属性表字段内容来分割,只需要在分割工具的参数中设置输入要素和分割要素均为同一要素,即我们要操作的要素,然后选择分割的字段即可。
780 0
Kotlin语法(类和对象)
二、类和对象: 1. 类定义: 类的声明包含类名,类头(指定类型参数,主构造函数等等),以及类主体,用大括号包裹。类头和类体是可选的;如果没有类体可以省略大括号。 class Invoice{ } 2. 构造函数: 在 Kotlin 中类可以有一个主构造函数以及多个二级构造函数。
734 0
基于继承类的属性模版中无法绑定的原因和解决方法
原文:基于继承类的属性模版中无法绑定的原因和解决方法 这个的晚上想学学WPF 做一个类似于ERP 左边菜单。构思一下思路 。。。。。。   创建一个类基于Expander类。 1 public class ExpanderBox : Expander 2 { 3 ...
673 0
+关注
刘桂林
心有菩提手有刀,欲成舍利却成妖
188
文章
0
问答
文章排行榜
最热
最新
相关电子书
更多
《2021云上架构与运维峰会演讲合集》
立即下载
《零基础CSS入门教程》
立即下载
《零基础HTML入门教程》
立即下载