76
The Kotlin Programming Language Svetlana Isakova

The Kotlin Programming Language, Svetlana Isakova

Embed Size (px)

DESCRIPTION

Talk given by Svetlana Isakova at scaladev'12 (scaladev.ru)

Citation preview

Page 1: The Kotlin Programming Language, Svetlana Isakova

The Kotlin Programming Language

Svetlana Isakova

Page 2: The Kotlin Programming Language, Svetlana Isakova

2

What? Who? Why?

A modern language Statically typed Object-oriented General-purpose

Compiler

JVM byte code JavaScript (not GWT)

Page 3: The Kotlin Programming Language, Svetlana Isakova

3

What? Who? Why?

A modern language Statically typed Object-oriented General-purpose

Developed by JetBrains

Open source Intended for industrial use

Page 4: The Kotlin Programming Language, Svetlana Isakova

4

Dynamic vs static typing

Dynamically typed languages Easier to learn Easier to write small programs

Statically typed languages Programs run much faster More powerful IDE Easier to support huge projects

Page 5: The Kotlin Programming Language, Svetlana Isakova

5

Scala as a candidate

Goal statically typed JVM-targeted concise language

Scala too complicated too implicit too difficult to create a good IDE

Page 6: The Kotlin Programming Language, Svetlana Isakova

6

Era of new industrial languages

Ceylon Red Hat / Jboss (April 2011) Scala Typesafe (May 2011) Kotlin JetBrains (July 2011) xTend Eclipse / itemis (November 2011)

Page 7: The Kotlin Programming Language, Svetlana Isakova

7

Kotlin “Hello, world”

fun main(args : Array<String>) {

    Greeter().greet()

}

class Greeter(name : String = "world") {

    val greeting = "Hello, $name!"

    fun greet() {

        println(greeting)

    }

}

Page 8: The Kotlin Programming Language, Svetlana Isakova

8

Problems and Solutions

Extending Existing APIs Handling Absent Values Case Analysis Multiple Implementation Inheritance Collection transformation Variance of Generic Types Builders

Page 9: The Kotlin Programming Language, Svetlana Isakova

9

Extending Existing APIs

Page 10: The Kotlin Programming Language, Svetlana Isakova

10

Regular expression example

Java

Pattern p = Pattern.compile("\\d*");

Matcher m = p.matcher("123");

if (m.find())

    String result = m.group();

Scala

val r = "\\d*".r

val result = r.findFirstIn("123")

Page 11: The Kotlin Programming Language, Svetlana Isakova

11

Scala: implicit conversions

val r = "\\d*".r 

trait StringOps { 

  ...

  def r: Regex = new Regex(toString)

implicit def augmentString(x: String)

                    = new StringOps(x)

Page 12: The Kotlin Programming Language, Svetlana Isakova

12

Scala: implicit conversions

val r = augmentString("\\d*").r 

trait StringOps { 

  ...

  def r: Regex = new Regex(toString)

implicit def augmentString(x: String)

                    = new StringOps(x)

Page 13: The Kotlin Programming Language, Svetlana Isakova

13

Scala: implicit conversions

val r = "\\d*".r

Conversion to 'StringOps' class: implicit requires a wrapper for each invocation

Page 14: The Kotlin Programming Language, Svetlana Isakova

14

Functionality extension

Java

Collections.sort(list, comparator)

Scala / Kotlin

list.sort(comparator)

'sort' is not declared in java.util.List 'sort' can be autocompleted

Page 15: The Kotlin Programming Language, Svetlana Isakova

15

Kotlin: extension functions

list.sort(comparator)

fun <T> List<T>.sort(c: Comparator<T>) {

    ...

}

Page 16: The Kotlin Programming Language, Svetlana Isakova

16

Iterator for String

for (c in “abc”) {    println(c)}

 

Page 17: The Kotlin Programming Language, Svetlana Isakova

17

Iterator for String

for (c in “abc”) {    println(c)}

class StringIterator(val s: String) :                         Iterator<Char> {    private var i = 0    override fun next() = s[i++]    override fun hasNext() = i < s.size}

Page 18: The Kotlin Programming Language, Svetlana Isakova

18

Iterator for String

for (c in “abc”) {    println(c)}

fun String.iterator() =                  StringIterator(this)

 

Page 19: The Kotlin Programming Language, Svetlana Isakova

19

Extension functions

fun <T> List<T>.sort(c:

               Comparator<T>) {...}

fun String.iterator() =

               StringIterator(this)

non-virtual compile to a static function

Page 20: The Kotlin Programming Language, Svetlana Isakova

20

Extending APIs

Scala implicit overhead on wrappers

Kotlin functionality cannot be inherited

Page 21: The Kotlin Programming Language, Svetlana Isakova

21

Handling Absent Values

Page 22: The Kotlin Programming Language, Svetlana Isakova

22

Java NPE problem

if (order.getCustomer().       //NPE

      getInfo().getAge() >

          limits.getMinLegalAge()) {

 ... 

}

Page 23: The Kotlin Programming Language, Svetlana Isakova

23

Java: @Nullable, @NotNull

@NotNull Customer getCustomer() {

   ...

   return null; //warning, assertion

}

@Nullable Customer getCustomer() {...}

getCustomer().getInfo() //warning, NPE

Page 24: The Kotlin Programming Language, Svetlana Isakova

24

Scala: Option type

def getCustomer() : Option[Customer] {…} 

order.getCustomer match {

   case Some(customer) =>

                Some(customer.getInfo)

   case None => None

 

Page 25: The Kotlin Programming Language, Svetlana Isakova

25

Scala: Option type

def getCustomer() : Option[Customer] {…} 

order.getCustomer match {

   case Some(customer) =>

                Some(customer.getInfo)

   case None => None

order.getCustomer.map(_.getInfo)

Page 26: The Kotlin Programming Language, Svetlana Isakova

26

Scala: Option type

def getCustomer() : Option[Customer] {

  ...

  return null //no error

}

Page 27: The Kotlin Programming Language, Svetlana Isakova

27

Scala: Option type

def getCustomer() : Option[Customer]  order.getCustomer.map(_.getInfo).

                         map(_.getAge) 

extra objects, classes are created: Some(customer), Some(info), Some(age) classes for function literals objects for function literals

 

inconvenient for debugging

Page 28: The Kotlin Programming Language, Svetlana Isakova

28

Kotlin: nullable types

fun getCustomer() : Customer? { 

    ...

    return null

}

fun getCustomer() : Customer {

    ...

    return null //error

}

Page 29: The Kotlin Programming Language, Svetlana Isakova

29

Kotlin: nullable types

fun getCustomer() : Customer? 

getCustomer().getInfo()   error 

getCustomer()?.getInfo()   ok 

 

Page 30: The Kotlin Programming Language, Svetlana Isakova

30

Kotlin: nullable types

fun getCustomer() : Customer? 

getCustomer().getInfo()   error 

getCustomer()?.getInfo()   // Info? 

Page 31: The Kotlin Programming Language, Svetlana Isakova

31

Kotlin: nullable types

fun getCustomer() : Customer? 

 

getCustomer()?.getInfo()   // Info? 

val customer = getCustomer()

 if (customer != null) 

  customer.getInfo()       // Info

Page 32: The Kotlin Programming Language, Svetlana Isakova

32

Call chains

Java

order.getCustomer().getInfo().getAge() 

Scala

order.getCustomer.map(_.getInfo).

                         map(_.getAge) Kotlin

order.getCustomer()?.getInfo()?.getAge()

Page 33: The Kotlin Programming Language, Svetlana Isakova

33

“If not null” check

Scala

opt foreach { value =>

   operate(value)

}

Kotlin

if (value != null) {

   operate(value)

}

Page 34: The Kotlin Programming Language, Svetlana Isakova

34

Java Interop

Scala

val files = new File("test").listFiles()

println(files.length) //NPE

Kotlin

val files = File("test").listFiles()

println(files.length) //doesn't compile

println(files?.size ?: "no files")

println(files!!.size) //NPE

Page 35: The Kotlin Programming Language, Svetlana Isakova

35

Kotlin & Java interop

@NotNull, @Nullable annotations

“alternative headers”

package java.util

public trait List<E> :                                  java.util.Collection<E> {

  ...

  fun listIterator() :                          java.util.ListIterator<E>

}

Page 36: The Kotlin Programming Language, Svetlana Isakova

36

Handling absent values

Scala overhead

Kotlin inconvenient Java interop without alternative

headers or annotations

Page 37: The Kotlin Programming Language, Svetlana Isakova

37

Case Analysis

Page 38: The Kotlin Programming Language, Svetlana Isakova

38

Scala: pattern matching

sealed trait Expr 

case class Num(value: Int) extends Expr 

case class Sum(left: Expr, right: Expr)                                        extends Expr

def eval(e: Expr) : Int =  

  e match { 

      case Num(v) => v 

      case Sum(l, r) => eval(l) + eval(r)            }

Page 39: The Kotlin Programming Language, Svetlana Isakova

39

Kotlin: smart casts

trait Expr 

class Number(val value: Int) : Expr 

class Sum(val left: Expr, val right: Expr):                                         Exprfun eval(e: Expr) : Int {

 

  if (e is Number)   

    return e.value     //smart cast 

   if (e is Sum)     return eval(e.left) + eval(e.right)

  

  throw IllegalArgumentException(                     “Unknown expression $e”)}

Page 40: The Kotlin Programming Language, Svetlana Isakova

40

Kotlin: smart casts

trait Expr 

class Num(val value: Int) : Expr 

class Sum(val left: Expr, val right: Expr):                                         Exprfun eval(e: Expr) : Int =

 

  when (e) {  

    is Num ­> e.value  

    is Sum ­> eval(e.left) + eval(e.right) 

    else ­> throw IllegalArgumentException(                     “Unknown expression $e”)  }

Page 41: The Kotlin Programming Language, Svetlana Isakova

41

Multiple Implementation Inheritance

Page 42: The Kotlin Programming Language, Svetlana Isakova

42

trait A {  val a = print("A")}

trait B {  val b = print("B")}

class C extends B with A {}

new C() 

Scala traits

Page 43: The Kotlin Programming Language, Svetlana Isakova

43

trait A {  val a = print("A")}

trait B {  val b = print("B")}

class C extends B with A {}

new C() // prints BA

Scala traits

Page 44: The Kotlin Programming Language, Svetlana Isakova

44

trait A {  val a = print("A")}

trait B extends A {  val b = print("B")}

class C extends B with A {}

new C() 

Scala traits

Page 45: The Kotlin Programming Language, Svetlana Isakova

45

trait A {  val a = print("A")}

trait B extends A {  val b = print("B")}

class C extends B with A {}

new C() // prints AB

Scala traits

Page 46: The Kotlin Programming Language, Svetlana Isakova

46

Scala traits

trait A {  def foo()}

trait B extends A {  override def foo() = "B"}

class C extends B {}

new C().foo()  //"B"

Page 47: The Kotlin Programming Language, Svetlana Isakova

47

Scala traits

trait A {  def foo()}

trait B extends A {  override def foo() = "B"}

trait D extends A {  override def foo() = "D"}

class C extends B with D {}

new C().foo()  //"D"

Page 48: The Kotlin Programming Language, Svetlana Isakova

48

Kotlin traits

are more like Java interfaces methods can have bodies

no state no linearization

Page 49: The Kotlin Programming Language, Svetlana Isakova

49

Kotlin traits

trait A {    fun foo() = println("A")} 

trait B {    fun foo() = println("B")} 

class C : B, A {} //doesn't compile                

Page 50: The Kotlin Programming Language, Svetlana Isakova

50

Kotlin traits

trait A {    fun foo() = println("A")} 

trait B {    fun foo() = println("B")} 

class C : B, A {    override fun foo() {        super<B>.foo()        super<A>.foo()    }}

Page 51: The Kotlin Programming Language, Svetlana Isakova

51

Collection transformation

Page 52: The Kotlin Programming Language, Svetlana Isakova

52

Scala collections

Set(1, 2, 3).map(_ * 0)    Set(0)→

"abc".map(_.toUpper)        → "ABC"

Page 53: The Kotlin Programming Language, Svetlana Isakova

53

Scala collections

Set(1, 2, 3).map(_ * 0)    Set(0)→

"abc".map(_.toUpper)        → "ABC"

trait TraversableLike[+A, +Repr] {

def map[B, That](f: A => B)(implicit bf:       CanBuildFrom[Repr, B, That]): That 

}

Page 54: The Kotlin Programming Language, Svetlana Isakova

54

Kotlin approach

'map', 'filter' always return immutable list

Page 55: The Kotlin Programming Language, Svetlana Isakova

55

Kotlin approach

'map', 'filter' always return immutable list

hashSet(1, 2, 3).map                     {(i: Int) ­> i * 0}                                List(0, 0, 0)→

Page 56: The Kotlin Programming Language, Svetlana Isakova

56

Kotlin approach

"abc".map {(c: Char) ­>                         c.toUpper}        → "ABC"

fun String.map(                            f : (Char) ­> Char) : String

Page 57: The Kotlin Programming Language, Svetlana Isakova

57

Lazy computations

Iterators are lazy set.iterator().map { … }.filter { … }

Page 58: The Kotlin Programming Language, Svetlana Isakova

58

Lazy computations

Iterators are lazy set.iterator().map { … }.filter { … }

Iterables are not lazy val lazySet = set.lazyMap { … }

lazySet().filter { … }

lazySet().filter { … }

Page 59: The Kotlin Programming Language, Svetlana Isakova

59

Variance of Generic Types

Page 60: The Kotlin Programming Language, Svetlana Isakova

60

Scala. Declaration site variance

class List[+T] { 

  //only produces T

  def head() : T 

  def tail() : List[T]

}

class Comparable[­T] { 

  //only consumes T

  def compare(t1 : T, t2: T)

}

Page 61: The Kotlin Programming Language, Svetlana Isakova

61

Kotlin. Declaration site variance

class List<out T> { 

  //only produces T

  fun head() : T 

  fun tail() : List[T]

}

class Comparable<in T> { 

  //only consumes T

  fun compare(t1 : T, t2: T)

}

Page 62: The Kotlin Programming Language, Svetlana Isakova

62

Use-site variance

fun <T> copy(from: Set<T>,                                to: Set<T>) {

  ...

}

copy(numbers, objects)

Page 63: The Kotlin Programming Language, Svetlana Isakova

63

Kotlin. Use-site variance

fun <T> copy(from: List<out T>,                            to: List<T>) {

  ...

}

copy(numbers, objects)

Page 64: The Kotlin Programming Language, Svetlana Isakova

64

Kotlin. Use-site variance

fun <T> copy(from: List<out T>,                            to: List<T>) {

  from.add(t) //error

  ...

}

copy(numbers, objects) 

Page 65: The Kotlin Programming Language, Svetlana Isakova

65

Scala. Use-site variance

def copy[T](from: Set[_ <: T],                              to: Set[T]) {

  ...

}

copy(numbers, objects)

Page 66: The Kotlin Programming Language, Svetlana Isakova

66

Scala. Existential types

def copy[T](from:

     Set[X] forSome { type X <: T },                      to: Set[T]) {

  ...

}

copy(numbers, objects)

Page 67: The Kotlin Programming Language, Svetlana Isakova

67

Builders

Page 68: The Kotlin Programming Language, Svetlana Isakova

68

Builders in Groovy

html {   head {      title "XML encoding with Groovy"   }

   body {      h1 "XML encoding with Groovy"      p "this format can be used as an                alternative markup to XML"      /* an element with attributes and text content */      ahref:'http://groovy.codehaus.org'["Groovy"]   }}

Page 69: The Kotlin Programming Language, Svetlana Isakova

69

Builders in Kotlin

html {   head {      title { + "XML encoding with Kotlin" }   }

   body {      h1 { + "XML encoding with Kotlin" }      p { + "this format this format is now type­safe" }

      /* an element with attributes and text content */      a(href = "http://kotlin.jetbrains.org")["Kotlin"]   }}

Page 70: The Kotlin Programming Language, Svetlana Isakova

70

Builders: Implementation Function definition

fun html(init : HTML.() ­> Unit) : HTML {

    val html = HTML()

    html.init()

    return html

}

Usage

html {

    this.head { ... }

}

Page 71: The Kotlin Programming Language, Svetlana Isakova

71

Builders: Implementation Function definition

fun html(init : HTML.() ­> Unit) : HTML {

    val html = HTML()

    html.init()

    return html

}

Usage

html {

    head { ... }

}

Page 72: The Kotlin Programming Language, Svetlana Isakova

72

Builders: Implementation

class Tag(val name : String) : Element {   val children = ArrayList<Element>()   val attributes = HashMap<String, String>()} class TagWithText(name : String) : Tag(name) {   fun String.plus() {       children.add(TextElement(this))   }} class HTML() : Tag("html") {   fun head(init : Head.() ­> Unit) { }   fun body(init : Body.() ­> Unit) { }}

Page 73: The Kotlin Programming Language, Svetlana Isakova

73

Builders in Kotlin

html {   head {      title { + "XML encoding with Kotlin" }   }

   body {      h1 { + "XML encoding with Kotlin" }      p { + "this format this format is now type­safe" }

      /* an element with attributes and text content */      a(href = "http://kotlin.jetbrains.org")["Kotlin"]   }}

Page 74: The Kotlin Programming Language, Svetlana Isakova

74

Resources

Home page

http://kotlin.jetbrains.org

Web Demo

http://kotlin­demo.jetbrains.com

Blog

http://blog.jetbrains.com/kotlin

Forum

Kotlin at http://devnet.jetbrains.com

Page 75: The Kotlin Programming Language, Svetlana Isakova

75

Interesting links

Marius Eriksen “Effective Scala” http://twitter.github.com/effectivescala/

Yang Zhang “True Scala complexity” http://yz.mit.edu/wp/true­scala­complexity/

Joshua Suereth D. “Scala in Depth”http://www.amazon.com/Scala­Depth­Joshua­Suereth­D/dp/1935182706

Page 76: The Kotlin Programming Language, Svetlana Isakova

Thank you!