Slide 1

Slide 1 text

Object-oriented programming in Kotlin

Slide 2

Slide 2 text

Feels the same …with some improvements

Slide 3

Slide 3 text

final, open, abstract public, private, internal The defaults are different

Slide 4

Slide 4 text

final, open, abstract public, private, /*package-private*/ The defaults are different internal explicit: non-final visible in a module

Slide 5

Slide 5 text

Different constructor syntax

Slide 6

Slide 6 text

Concise primary constructor class Person(val name: String, val age: Int)

Slide 7

Slide 7 text

Full primary constructor syntax (1) class Person(name: String) { init { } } constructor parameter constructor body

Slide 8

Slide 8 text

Full primary constructor syntax (2) class Person(name: String) { val name: String init { this.name = name } } constructor parameter constructor body

Slide 9

Slide 9 text

val/var on parameter creates a property class Person(name: String) { val name: String init { this.name = name } } class Person(val name: String) is the same as:

Slide 10

Slide 10 text

Secondary constructor class Rectangle(val height: Int, val width: Int) { constructor(side: Int) : this(side, side) { … } } secondary constructor primary constructor

Slide 11

Slide 11 text

Properties, not fields

Slide 12

Slide 12 text

property = field + accessor(s) read-only property = field + getter mutable property = field + getter + setter Property ( val / var )

Slide 13

Slide 13 text


 class Contact( val name: String, var address: String ) contact.getAddress(); contact.setAddress("..."); contact.address contact.address = "..."

Slide 14

Slide 14 text

property = field? + accessor(s) read-only property = field? + getter mutable property = field? + getter + setter Property ( val / var )

Slide 15

Slide 15 text

class Rectangle(val height: Int, val width: Int) { val isSquare: Boolean get() { return height == width } } Backing field might be absent

Slide 16

Slide 16 text

class StateLogger { var state = false set(value) { println("state has changed") field = value } } You can use field inside accessors (only)

Slide 17

Slide 17 text

val foo: Int val is read-only property (not immutable) get() = Random().nextInt()

Slide 18

Slide 18 text

Classes

Slide 19

Slide 19 text

Class modifiers enum, data, inner, sealed

Slide 20

Slide 20 text

Enum class import Color.* fun getDescription(color: Color) = when (color) { BLUE -> "cold" ORANGE -> "mild" RED -> "hot" } enum class Color { BLUE, ORANGE, RED } represents enumeration

Slide 21

Slide 21 text

Data modifier data class Contact(val name: String, val address: String) generates useful methods: equals, hashCode, copy, toString, and some others contact.copy(address = "new address")

Slide 22

Slide 22 text

Equals & reference equality val set1 = setOf(1, 2, 3) val set2 = setOf(1, 2, 3) set1 == set2 set1 === set2 checks reference equality calls equals true false

Slide 23

Slide 23 text

Sealed modifier sealed class Expr class Num(val value: Int) : Expr() class Sum(val left: Expr, val right: Expr) : Expr() restricts class hierarchy: all subclasses must be located in the same file fun eval(e: Expr): Int = when (e) { is Num -> e.value is Sum -> eval(e.left) + eval(e.right) }

Slide 24

Slide 24 text

Inner modifier adds reference to the outer class class A { class B inner class C { …this@A… } }

Slide 25

Slide 25 text

interface Repository { fun getById(id: Int): Customer fun getAll(): List } interface Logger { fun logAll() } class Controller( repository: Repository, logger: Logger ) : Repository by repository, Logger by logger fun use(controller: Controller) { controller.logAll() } Class delegation

Slide 26

Slide 26 text

Objects & companion objects

Slide 27

Slide 27 text

object = singleton object KSingleton { fun foo() {} }

Slide 28

Slide 28 text

Object = singleton public class JSingleton { public final static JSingleton INSTANCE = new JSingleton(); private JSingleton() { } public void foo() {} } object KSingleton { fun foo() {} }

Slide 29

Slide 29 text

Using Kotlin object from Java public class UsingKotlinObjectFromJava { public static void main(String[] args) { JSingleton.INSTANCE.foo(); KSingleton.INSTANCE.foo(); } }

Slide 30

Slide 30 text

companion object class A { companion object { fun foo() = 1 } } fun main(args: Array) { A.foo() } special object inside a class

Slide 31

Slide 31 text

companion object can implement an interface interface Factory { fun create(): T } class A { private constructor() companion object : Factory { override fun create(): A { return A() } }

Slide 32

Slide 32 text

No static keyword Declare “static” members: - at the top-level - inside objects - inside companion objects

Slide 33

Slide 33 text

@JvmStatic class C {
 companion object {
 @JvmStatic fun foo() {}
 fun bar() {}
 }
 } // Java
 C.foo();
 C.bar(); C.Companion.foo(); C.Companion.bar();

Slide 34

Slide 34 text

@JvmStatic object Obj {
 @JvmStatic fun foo() {}
 fun bar() {}
 } // Java Obj.foo();
 Obj.bar();
 Obj.INSTANCE.foo(); Obj.INSTANCE.bar();

Slide 35

Slide 35 text

Constants • const (for primitive types and String) • @JvmField

Slide 36

Slide 36 text

Compile-time constants for primitive types and String const val answer = 42 the value is inlined

Slide 37

Slide 37 text

@JvmField @JvmField val property = MyClass() // the same as // Java public static final MyClass property = new MyClass(); exposes a Kotlin property as a field in Java

Slide 38

Slide 38 text

@JvmField makes a property static if used inside object class A { @JvmField val property = MyClass() } object B { @JvmField val property = MyClass() } regular field generated static field generated

Slide 39

Slide 39 text

Annotations

Slide 40

Slide 40 text

Annotation syntax @file:JvmName("FooUtils") use-site target annotation name annotation arguments

Slide 41

Slide 41 text

Why use-site target? @Rule var folder @property:Rule @field:Rule @getter:Rule @setter:Rule might be:

Slide 42

Slide 42 text

@JvmName // Data.kt fun foo() {
 } public final class DataKt {
 public static void foo() {
 }
 } @file:JvmName("FooUtils") fun foo() {
 } public final class FooUtils {
 public static final void foo() {
 }
 }

Slide 43

Slide 43 text

@JvmName fun List.filterValid(): List
 fun List.filterValid(): List Error: platform declaration clash: declarations have the same JVM signature (filterValid(Ljava/util/List;)Ljava/util/List;)

Slide 44

Slide 44 text

@JvmName fun List.filterValid(): List
 @JvmName("filterValidInt")
 fun List.filterValid(): List

Slide 45

Slide 45 text

@JvmOverloads 
 fun f(a: String, b: Int = 0, c: String = "abc") {
 // ...
 } // Java
 void f(String a, int b, String c) { }


Slide 46

Slide 46 text

@JvmOverloads @JvmOverloads
 fun f(a: String, b: Int = 0, c: String = "abc") {
 // ...
 } // Java
 void f(String a, int b, String c) { }
 void f(String a, int b) { }
 void f(String a) { }

Slide 47

Slide 47 text

@Throws @Throws(IOException::class)
 fun foo() {
 throw IOException()
 }

Slide 48

Slide 48 text

Checked exceptions // Java
 try {
 DemoKt.foo();
 }
 catch (IOException e) {
 // ...
 } fun foo() { throw IOException() } Error: Exception java.io.IOException is never thrown in body of corresponding try statement

Slide 49

Slide 49 text

Checked exceptions // Java
 try {
 DemoKt.foo();
 }
 catch (IOException e) {
 // ...
 } @Throws(IOException::class) fun foo() { throw IOException() }

Slide 50

Slide 50 text

Copyright © 2017 https://github.com/JetBrains/kotlin-workshop