Kotlin revealed

Julien WITTOUCK

Au menu

  • What is Kotlin?
  • Kotlin main language features
  • Why Kotlin is my next programming language?

What is Kotlin?

Kotlin is..

A programming language

Object Oriented

Functionnal

Kotlin is...

Designed for the JVM and Android

Works everywhere where Java works

  • Server side applications
  • Android applications
  • Desktop applications

Kotlin...

Works with all major Java tools/frameworks

  • IntelliJ IDEA, Android Studio, Eclipse
  • Maven, Gradle, Ant
  • Spring/Hibernate...
  • Github, Slack, and even Minecraft

Kotlin is...

Interoperable with Java

  • Mixed Java+Kotlin projects
  • Usage of Java libraries in Kotlin
  • Usage of Kotlin libraries in Java

Kotlin is...

Production-ready

  • Version 1.0 released on feb. 2016
  • 500k lines of code in Jetbrains projects
  • 2M lines of code in Github

Companies using Kotlin

  • Jetbrains : IntelliJ IDEA plugins, YouTrack vNext, CRM apps, new products etc.
  • Prezi.com : Kotlin in backend, data processing and service development
  • NBC News Digital : NBC News, TODAY and Nightly News Android apps using Kotlin

Getting started

Language basics

Defining packages

package my.demo

import java.util.*

// ...

Language basics

Defining functions

Function having two Int parameters with Int return type:

fun sum(a: Int, b: Int): Int {
  return a + b
}

Function with an expression body and inferred return type:

fun sum(a: Int, b: Int) = a + b

Language basics

Defining functions

Function returning no meaningful value:

fun printSum(a: Int, b: Int): Unit {
  print(a + b)
}

Unit return type can be omitted:

fun printSum(a: Int, b: Int) {
  print(a + b)
}

Language basics

Expressions

This statement :

fun max(a: Int, b: Int): Int {
  if (a > b)
    return a
  else
    return b
}

can be re-writen in a one-liner, using if as an expression

fun max(a: Int, b: Int) = if (a > b) a else b

Language basics

Defining variables

Assign-once (read-only) local variable:

val a: Int = 1
val b = 1   // `Int` type is inferred
val c: Int  // Type required when no initializer is provided
c = 1       // definite assignment

Mutable variable:

var x = 5 // `Int` type is inferred
x += 1

Language basics

String templates

fun example1(a: Any, b: Any) =
  "This is some text in which variables ($a, $b) appear."

WHat does it look like?

A POJO with getters, setters, equals(), hashCode(), toString() and copy() in a single line:

data class Customer(val name: String, val email: String, val company: String)

Named & default arguments

fun bar(i: Int, s: String = "", b: Boolean = true) {}

fun usage() {
    // named arguments:
    bar(1, b = false)
}

The billion dollar mistake (1965)

All use of references should be absolutely safe, with checking performed automatically by the compiler. But I couldn't resist the temptation to put in a null reference, simply because it was so easy to implement. This has led to innumerable errors, vulnerabilities, and system crashes, which have probably caused a billion dollars of pain and damage in the last forty years.

null

A regular variable cannot hold a null reference

var a: String = "abc"
a = null // compilation error
val l = a.length // ok: variable 'a' will never be null

To allow nulls, we can declare a variable as nullable using ?

var b: String? = "abc"
a = null // ok
val l = b.length // error: variable 'b' can be null

null

Checking for null in conditions

val l = if (b != null) b.length else -1

Safe Calls '?'

val l = b?.length // returns b.length if b is not null, and null otherwise

Elvis operator ?:

val l = b?.length ?: -1

If the expression to the left of ?: is not null, the elvis operator returns it, otherwise it returns the expression to the right

Extension functions

Extend a class without having to inherit from the class or use a Decorator pattern

Collections.sort( myList, myComparator );
fun List.sort( myComparator ) {
    Collections.sort(this, myComparator )
}

myList.sort(myComparator)
                        
fun String.toCamelCase() { ... }

"Convert this to camelcase".toCamelCase()

Collections

Immutable & Mutable collections

  • List<T> / MutableList<T>
  • Set<T> / MutableSet<T>
  • Map<T> / MutableMap<T>
val numbers: MutableList<Int> = mutableListOf(1, 2, 3)
val readOnlyView: List<Int> = numbers
println(numbers)      // prints "[1, 2, 3]"
numbers.add(4)
println(readOnlyView) // prints "[1, 2, 3, 4]"
readOnlyView.clear()  // -> does not compile
                      // 'clear' is not in the Immutable interface

Collection extensions

val items = listOf(1, 2, 3, 4)
items.first() == 1
items.last() == 4
items.filter { it % 2 == 0 }   // returns [2, 4]
// have you seen the Lambda ?

val rwList = mutableListOf(1, 2, 3)
rwList.requireNoNulls()        // returns [1, 2, 3]
if (rwList.none { it > 6 }) println("No items above 6")
// prints "No items above 6"
val item = rwList.firstOrNull()

Higher-Order Functions and Lambdas

Functions that takes functions as a parameter

fun <T, R> List<T>.map(transform: (T) -> R): List<R> {
  val result = arrayListOf<R>()
  for (item in this)
    result.add(transform(item))
  return result
}
val doubled = ints.map { it -> it * 2 } // or : ints.map { it * 2 }

strings.filter { it.length == 5 }.map { it.toUpperCase() }

Why Kotlin is my next programming language?

Concise

Less boilerplate code (POJOs)

Why Kotlin is my next programming language?

Safe

Say bye-bye to NullPointerExceptions

Why Kotlin is my next programming language?

Interoperable

Works with my favorites frameworks

Thank you!

Questions?