您的位置:首页 > 其它

Kotlin类和对象(三)——接口与访问修饰符

2017-10-22 17:05 246 查看
接口
实现接口

接口中的属性

解决重写冲突

访问修饰符


类和接口
构造函数

局部声明

模块

接口

Kotlin的接口和Java 8的接口很相似。它们可以包含抽象方法也可以包含方法的实现。与抽象类不同的地方在于,接口不可以存储状态。它们可以拥有属性,但是必须是抽象的或者提供访问器的实现。

使用关键词
interface
定义接口:

interface MyInterface {
fun bar()
fun foo() {
// 可选的方法体
}
}


实现接口

一个类或对象,可以实现一个或多个接口

class Child : MyInterface {
override fun bar() {
// body
}
}


接口中的属性

你可以在接口中声明属性,接口中声明的属性可以使抽象的也可以提供访问器的实现。但是声明在接口中的属性,不可以有幕后字段,因此定义在接口中的访问器不能引用它们。

interface MyInterface {
val prop: Int // 抽象属性
val propertyWithImplementation: String
get() = "foo"
fun foo() {
print(prop)
}
}
class Child : MyInterface {
verride val prop: Int = 29
}


解决重写冲突

当我们在超级类型列表中声明多个类型时,会发现我们继承了不止一个相同方法的实现。如:

interface A {
fun foo() { print("A") }
fun bar()
}
interface B {
fun foo() { print("B") }
fun bar() { print("bar") }
}
class C : A {
override fun bar() { print("bar") }
}
class D : A, B {
override fun foo() {
super<A>.foo()
super<B>.foo()
}
override fun bar() {
super<B>.bar()
}
}


接口A和接口B都申明了函数foo()和bar()。它们都实现了foo(),只有B实现了bar(),(A中的bar()没有用abstract标记,因为在接口中,如果函数没有函数体,那么该函数默认是抽象函数)。现在,如果我们从A类生成一个具体的C类,我们显然需要重写bar()和提供一个实现。

然而,如果我们从A和B类生成一个具体的D类,我们需要实现从多个接口中继承过来的所有方法,而且详细说明D需要怎样完全的实现它们。这个规则用于我们继承的单个实现(bar())和多个实现(foo())方法。

访问修饰符

类、对象、接口、构造函数、函数、属性和它的setter可以有访问修饰符(getter通常和属性有相同的访问属性)。Kotlin中有4个访问修饰符:private、protected、internal和public。如果没有使用显示的修饰符,将会使用默认的访问属性public。

函数、属性和类、对象和接口都可以定义在顶层(top-level),即,直接在包内:

// 文件名: example.kt
package foo

fun baz() {} //顶层的函数
class Bar {} //顶层的类


如果你没有具体说明任何修饰符,就默认使用public,这样你声明的包,就可以在任何地方被访问。

如果你声明为private,那就只能在包含声明的文件内部可以访问。

如果你声明为internal,它就可以在同一个模块的任何地方可以访问。

protected在顶层声明中不可以使用。

如:

// 文件名: example.kt
package foo

private fun foo() {} // foo只在example.kt内可以访问
public var bar: Int = 5 // bar可以在任何地方范文。
private set // setter 只在 example.kt内可以访问

internal val baz = 6// 在相同的模块中可以访问。


类和接口

当在类中声明成员时:

private 只能在类内部可以访问(包括它所有的成员)。

protected 不仅可以在类内部访问,还可以在子类中访问。

internal 在本模块中可以访问到声明类的终端就可以访问到声明的internal成员。

public 所有可以访问到声明类的终端就可以访问到声明的public成员。

例子:

open class Outer {
private val a = 1
protected open val b = 2
internal val c = 3
val d = 4 // 默认是public

protected class Nested {
public val e: Int = 5
}
}

class Subclass : Outer() {//集成Outer类
// a 不可以访问
// b, c 可以访问
// Nested 和 e 可以访问

override val b = 5 // 'b' 是protected可以被重写
}

class Unrelated(o: Outer) {//引用Outer类
// o.a, o.b 不可以访问
// o.c 和 o.d 可以访问 (相同模块)
// Outer.Nested 不可以访问, 而且 Nested::e 也不可以访问
}


构造函数

使用下面的句法(你需要显示使用关键词constructor)来具体说明类的主构造函数访问权限。

class C private constructor(a: Int) { ... }


这里的构造函数是private。所有的构造函数默认都是public,只要类可以被访问,它的构造函数也就可以被访问。(即,一个internal 类的构造函数只能在相同的模块中访问)。

局部声明

局部声明的变量、函数和类都不可以有访问修饰符。

模块

使用访问修饰符internal表示成员只能在相同的模块中访问。更明确地说,模块就是一系列的Kotlin文件编译在一起。

一个IntelliJ IDEA模块

一个Maven项目

一个Gradle源码集合

Ant任务执行一次编译的一组文件
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: 
相关文章推荐