Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Kotlin - The Next Hot Thing on the JVM

Kotlin - The Next Hot Thing on the JVM

Introduction to Kotlin for Java programmers.

Avatar for Tomche Delev

Tomche Delev

April 05, 2017
Tweet

More Decks by Tomche Delev

Other Decks in Programming

Transcript

  1. Java Limitations • Verbose • Limited type inference • No

    properties • Checked exceptions • Null Pointer Exceptions • Extensibility • End of lines ; • Java Puzzlers • We deserve a better solution than Lombok...
  2. What makes Java great • Fast • Optimized bytecode •

    Static typing • Simple to learn • Amazing ecosystem
  3. Kotlin facts • July 2011 JetBrains unveiled Project Kotlin, a

    new language for the JVM • Designed by: JetBrains • Version v1.0: was released on February 15, 2016 • Stable release: Kotlin 1.0.6 / December 27, 2016 • License: Apache 2 • Filename extension: .kt .kts • Preview release: Kotlin 1.1.0-beta-17 / January 19, 2017;
  4. Defining functions fun printSum(a: Int, b: Int): Unit { print(a

    + b) } fun printSum(a: Int, b: Int) { print(a + b) }
  5. Defining local variables 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
  6. Using string templates fun main(args: Array<String>) { if (args.size ==

    0) return print("First argument: ${args[0]}") }
  7. Using nullable values and checking for null A reference must

    be explicitly marked as nullable when null value is possible. fun parseInt(str: String): Int? { // ... }
  8. Using nullable values and checking for null fun main(args: Array<String>)

    { if (args.size < 2) { print("Two integers expected") return } val x = parseInt(args[0]) val y = parseInt(args[1]) // Using `x * y` yields error because they may hold nulls. if (x != null && y != null) { // x and y are automatically cast to non-nullable after null check print(x * y) } }
  9. Using type checks and automatic casts fun getStringLength(obj: Any): Int?

    { if (obj is String) { // `obj` is automatically cast to `String` in this branch return obj.length } // `obj` is still of type `Any` outside of the type-checked branch return null }
  10. Using a for loop fun main(args: Array<String>) { for (arg

    in args) { print(arg) } } OR for (i in args.indices) { print(args[i]) }
  11. Using a while loop fun main(args: Array<String>) { var i

    = 0 while (i < args.size) { print(args[i++]) } }
  12. Using when expression fun cases(obj: Any) { when (obj) {

    1 -> print("One") "Hello" -> print("Greeting") is Long -> print("Long") !is String -> print("Not a string") else -> print("Unknown") } }
  13. Using ranges if (x in 1..y-1) { print("OK") } if

    (x !in 0..array.lastIndex) { print("Out") } for (x in 1..5) { print(x) }
  14. Using collections for (name in names) { println(name) } if

    (text in names) { // names.contains(text) is called print("Yes") } names.filter { it.startsWith("A") } .sortedBy { it } .map { it.toUpperCase() } .forEach { print(it) }
  15. Creating DTOs (POJOs/POCOs) data class User(val name: String, val age:

    Int) provides a User class with the following functionality: • getters (and setters in case of vars) for all properties • equals() • hashCode() • toString() • copy() • component1(), component2(), …, for all properties
  16. Filtering a list val positives = list.filter { x ->

    x > 0 } val positives = list.filter { it > 0 }
  17. Using ranges for (i in 1..100) { ... } //

    closed range: includes 100 for (i in 1 until 100) { ... } // half-open range: does not include 100 for (x in 2..10 step 2) { ... } for (x in 10 downTo 1) { ... } if (x in 1..10) { ... }
  18. Executing a statement if null val data = ... val

    email = data["email"] ?: throw IllegalStateException("Email is missing!")
  19. Execute if not null val data = ... data?.let {

    ... // execute this block if not null }
  20. Return on when statement fun transform(color: String): Int { return

    when (color) { "Red" -> 0 "Green" -> 1 "Blue" -> 2 else -> throw IllegalArgumentException("Invalid color param value") } }
  21. 'try/catch' expression fun test() { val result = try {

    count() } catch (e: ArithmeticException) { throw IllegalStateException(e) } // Working with result }
  22. 'if' expression fun foo(param: Int) { val result = if

    (param == 1) { "one" } else if (param == 2) { "two" } else { "three" } }
  23. Builder-style usage of methods that return Unit fun arrayOfMinusOnes(size: Int):

    IntArray { return IntArray(size).apply { fill(-1) } }
  24. Single-expression functions fun theAnswer() = 42 fun theAnswer(): Int {

    return 42 } fun transform(color: String): Int = when (color) { "Red" -> 0 "Green" -> 1 "Blue" -> 2 else -> throw IllegalArgumentException("Invalid color") }
  25. Calling multiple methods on an object instance('with') class Turtle {

    fun penDown() fun penUp() fun turn(degrees: Double) fun forward(pixels: Double) } val myTurtle = Turtle() with(myTurtle) { //draw a 100 pix square penDown() for(i in 1..4) { forward(100.0) turn(90.0) } penUp() }
  26. Convenient form for a generic function that requires the generic

    type information // public final class Gson { // ... // public <T> T fromJson(JsonElement json, Class<T> classOfT) throws JsonSyntaxException { // ... inline fun <reified T: Any> Gson.fromJson(json): T = this.fromJson(json, T::class.java)
  27. Consuming a nullable Boolean val b: Boolean? = ... if

    (b == true) { ... } else { // `b` is false or null }
  28. Other Kotlin goodness waiting for you... • Extension functions and

    extension properties • Generics with declaration-site and use-site variance • Class delegation and delegated properties • Destructuring declarations • Operator overloading • Type-safe builders • ...