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

Kotlin for Java Developers (GDG Leeds June 2017)

Kotlin for Java Developers (GDG Leeds June 2017)

Darren Atherton

June 08, 2017
Tweet

More Decks by Darren Atherton

Other Decks in Programming

Transcript

  1. KOTLIN FOR JAVA DEVELOPERS WHAT IS KOTLIN? ▸ Statically-typed JVM

    language from JetBrains. ▸ OOP language with functional aspects. ▸ Focuses on safe, concise code while maintaining (and increasing) readability. ▸ First-class tooling support. ▸ Now officially supported by Google. KOTLIN
  2. KOTLIN OPERABILITY WITH JAVA TECHNOLOGIES ▸ Android ▸ Android Studio

    2.3 - requires plugin installation. ▸ Android Studio 3.0 (alpha) - no setup required.
 ▸ Spring/Spring Boot ▸ Spring Framework 5.0 - dedicated Kotlin support using Kotlin Extension functions. ▸ Spring Boot Initializr - can choose Kotlin as a language: https://start.spring.io
 ▸ Eclipse Vert.x KOTLIN FOR JAVA DEVELOPERS KOTLIN
  3. PROPERTIES KOTLIN FOR JAVA DEVELOPERS KOTLIN ▸ Properties are fields

    with auto-generated getters and setters. val name: String = "Darren" ▸ Immutable, equivalent to final var name: String = "Darren" name = "Still Darren" ▸ Mutable val name = "Darren" ▸ Types are auto-inferred ▸ Prefer val over var - code with immutable fields is less likely to contain bugs!
  4. VISIBILITY MODIFIERS - CLASS LEVEL KOTLIN FOR JAVA DEVELOPERS KOTLIN

    ▸ For members declared inside a class: ▸ Private - member is visible inside the class only. ▸ Protected - member has the same rules as private but is also available in subclasses. ▸ Internal - any member inside the same module can see internal members ▸ Public - any member who can see the class can see it’s public members. ▸ Default visibility is public.
  5. VISIBILITY MODIFIERS - TOP LEVEL KOTLIN FOR JAVA DEVELOPERS KOTLIN

    ▸ For declarations declared inside at the top level: ▸ Private - declaration only visible in the same file. ▸ Protected - not available as the top level is independent of any class hierarchy. ▸ Internal - declaration visible only in the same module. ▸ Public - declaration is visible everywhere. ▸ Default visibility is public.
  6. internal fun sum(first: Int, second: Int): Int { return first

    + second } FUNCTION SYNTAX KOTLIN FOR JAVA DEVELOPERS KOTLIN ▸ Access modifier ▸ Name ▸ Param name/type ▸ Return type ▸ Keyword
  7. FUNCTION SYNTAX - VARIATIONS KOTLIN FOR JAVA DEVELOPERS internal fun

    sum(first: Int, second: Int): Int { return first + second } KOTLIN ▸ Full syntax
  8. FUNCTION SYNTAX KOTLIN FOR JAVA DEVELOPERS internal fun sum(first: Int,

    second: Int): Int { return first + second } fun sum(first: Int, second: Int): Int { return first + second } KOTLIN ▸ Full syntax ▸ Omit access modifier FUNCTION SYNTAX - VARIATIONS
  9. FUNCTION SYNTAX KOTLIN FOR JAVA DEVELOPERS internal fun sum(first: Int,

    second: Int): Int { return first + second } fun sum(first: Int, second: Int): Int { return first + second } fun sum(first: Int, second: Int): Int = first + second KOTLIN ▸ Full syntax ▸ Omit access modifier ▸ Inline return FUNCTION SYNTAX - VARIATIONS
  10. FUNCTION SYNTAX KOTLIN FOR JAVA DEVELOPERS internal fun sum(first: Int,

    second: Int): Int { return first + second } fun sum(first: Int, second: Int): Int { return first + second } fun sum(first: Int, second: Int): Int = first + second fun sum(first: Int, second: Int) = first + second KOTLIN ▸ Full syntax ▸ Omit access modifier ▸ Inline return ▸ Omit return type FUNCTION SYNTAX - VARIATIONS
  11. FUNCTION SYNTAX KOTLIN FOR JAVA DEVELOPERS internal fun sum(first: Int,

    second: Int): Int { return first + second } fun sum(first: Int, second: Int): Int { return first + second } fun sum(first: Int, second: Int): Int = first + second fun sum(first: Int, second: Int) = first + second val sum = { first: Int, second: Int -> first + second } val sum: (Int, Int) -> Int = { first, second -> first + second } KOTLIN ▸ Full syntax ▸ Omit access modifier ▸ Inline return ▸ Omit return type ▸ As a type FUNCTION SYNTAX - VARIATIONS
  12. internal fun sum(first: Int, second: Int): Int { return first

    + second } FUNCTIONS - NAMED PARAMETERS KOTLIN FOR JAVA DEVELOPERS KOTLIN ▸ Parameter name ▸ Parameter type val total = sum(first = 2, second = 2) val total = sum(second = 2, first = 2)
  13. FUNCTIONS - DEFAULT AND OPTIONAL PARAMETERS KOTLIN FOR JAVA DEVELOPERS

    KOTLIN internal fun sum(first: Int = 2, second: Int): Int { return first + second } val total = sum(second = 2)
  14. FUNCTIONS - DEFAULT AND OPTIONAL PARAMETERS KOTLIN FOR JAVA DEVELOPERS

    JAVA void showText(String text, float fontSize, String typeface) { }
  15. FUNCTIONS - DEFAULT AND OPTIONAL PARAMETERS KOTLIN FOR JAVA DEVELOPERS

    JAVA void showText(String text, float fontSize, String typeface) { } void showText(String text, String typeface) { showText(text, DEFAULT_FONT_SIZE, typeface); }
  16. FUNCTIONS - DEFAULT AND OPTIONAL PARAMETERS KOTLIN FOR JAVA DEVELOPERS

    JAVA void showText(String text, float fontSize, String typeface) { } void showText(String text, String typeface) { showText(text, DEFAULT_FONT_SIZE, typeface); } void showText(String text, float fontSize) { showText(text, fontSize, DEFAULT_TYPEFACE); }
  17. FUNCTIONS - DEFAULT AND OPTIONAL PARAMETERS KOTLIN FOR JAVA DEVELOPERS

    JAVA void showText(String text, float fontSize, String typeface) { } void showText(String text, String typeface) { showText(text, DEFAULT_FONT_SIZE, typeface); } void showText(String text, float fontSize) { showText(text, fontSize, DEFAULT_TYPEFACE); } void showText(String text) { showText(text, DEFAULT_FONT_SIZE, DEFAULT_TYPEFACE); }
  18. FUNCTIONS - DEFAULT AND OPTIONAL PARAMETERS KOTLIN FOR JAVA DEVELOPERS

    KOTLIN fun showText(text: String, fontSize: Float = DEFAULT_FONT_SIZE, typeface: String = DEFAULT_TYPEFACE) {} ▸ Defaults showText("hello world") showText("hello world", 16f) showText("hello world", 16f, "Arial") showText("hello world", typeface = "Arial") showText("hello world", fontSize = 16f) showText(text = "hello world", fontSize = 16f, typeface = "Arial") ▸ Using order ▸ Using names
  19. HIGHER-ORDER FUNCTIONS KOTLIN FOR JAVA DEVELOPERS KOTLIN ▸ Functions which

    return a function or take a function as a parameter ▸ Predominantly used via lambdas ▸ Available at the Java 6 level (great for Android!) fun <T> Iterable<T>.filter(predicate: (T) -> Boolean): List<T> { return filterTo(ArrayList<T>(), predicate) } val list: List<String> = listOf("Darren") val filtered = list.filter { it.startsWith("D") } val filtered = list.filter { singleString -> singleString.startsWith("D") }
  20. NULLABILITY KOTLIN FOR JAVA DEVELOPERS JAVA/KOTLIN ▸ In Java, the

    NullPointerException is one of the biggest sources of errors. ▸ In Kotlin, ‘null’ is part of the type system. ▸ For each property, we can declare whether it can contain a nullable value. ▸ For each function, we can declare whether it returns a nullable value. ▸ This eliminates the NullPointerException*.
  21. NULLABILITY KOTLIN FOR JAVA DEVELOPERS JAVA/KOTLIN String myString = generateSomeString();

    // method can return null String myString2 = myString.replace("old", "new"); ▸ Throws NPE!
  22. NULLABILITY KOTLIN FOR JAVA DEVELOPERS JAVA/KOTLIN String myString = generateSomeString();

    // method can return null String myString2 = myString.replace("old", "new"); ▸ Throws NPE! val myString: String? = generateSomeString() val myString2 = myString.replace("old", "new") ▸ Does not compile
  23. NULLABILITY KOTLIN FOR JAVA DEVELOPERS JAVA/KOTLIN String myString = generateSomeString();

    // method can return null String myString2 = myString.replace("old", "new"); ▸ Throws NPE! val myString: String? = generateSomeString() val myString2 = myString.replace("old", "new") ▸ Does not compile if (myString != null) { val myString2 = myString.replace("old", "new") } ▸ Compiles!
  24. HANDLING NULL VALUES KOTLIN FOR JAVA DEVELOPERS KOTLIN if (myString

    != null) { val myString2 = myString.replace("old", "new") } ▸ Classic null-check
  25. HANDLING NULL VALUES KOTLIN FOR JAVA DEVELOPERS KOTLIN if (myString

    != null) { val myString2 = myString.replace("old", "new") } val myString2 = myString?.replace("old", "new") ▸ Classic null-check ▸ Safe-call operator
  26. HANDLING NULL VALUES KOTLIN FOR JAVA DEVELOPERS KOTLIN if (myString

    != null) { val myString2 = myString.replace("old", "new") } val myString2 = myString?.replace("old", "new") val myString2 = myString?.replace("old", "new") ?: "default" ▸ Classic null-check ▸ Safe-call operator ▸ Elvis operator
  27. NULLABILITY KOTLIN FOR JAVA DEVELOPERS @Nullable public Account getAccountForUsername(@Nullable String

    username) { if (username != null) { return accountManager.getAccount(username); } else { return null; } } JAVA/KOTLIN
  28. NULLABILITY KOTLIN FOR JAVA DEVELOPERS @Nullable public Account getAccountForUsername(@Nullable String

    username) { if (username != null) { return accountManager.getAccount(username); } else { return null; } } fun getAccountForUsername(username: String?): Account? { return if (username != null) { accountManager.getAccount(username) } else { null } } JAVA/KOTLIN
  29. DATA CLASSES KOTLIN FOR JAVA DEVELOPERS public class VideoGame {

    private String name; private String publisher; private int reviewScore; public VideoGame(String name, String publisher, int reviewScore) { this.name = name; this.publisher = publisher; this.reviewScore = reviewScore; } } JAVA
  30. DATA CLASSES KOTLIN FOR JAVA DEVELOPERS public String getName() {}

    public void setName(String name) {} public String getPublisher() {} public void setPublisher(String publisher) {} public int getReviewScore() {} public void setReviewScore(int reviewScore) {} JAVA
  31. DATA CLASSES KOTLIN FOR JAVA DEVELOPERS public boolean equals(Object o)

    { if (this == o) return true; if (o == null || getClass() != o.getClass()) return false; VideoGame that = (VideoGame) o; if (reviewScore != that.reviewScore) return false; if (name != null ? !name.equals(that.name) : that.name != null) { return false; } return publisher != null ? publisher.equals(that.publisher) : that.publisher == null; } JAVA
  32. DATA CLASSES KOTLIN FOR JAVA DEVELOPERS @Override public int hashCode()

    { int result = name != null ? name.hashCode() : 0; result = 31 * result + (publisher != null ? publisher.hashCode() : 0); result = 31 * result + reviewScore; return result; } @Override public String toString() { return "VideoGame{" +"name='" + name + '\'' + ", publisher='" + publisher + '\'' + ", reviewScore=" + reviewScore +'}'; } JAVA
  33. ▸ By specifying the ‘data’ keyword, we get all of

    this for free and some extras. DATA CLASSES KOTLIN FOR JAVA DEVELOPERS KOTLIN data class VideoGame(val name: String, val publisher: String, var reviewScore: Int)
  34. DATA CLASSES KOTLIN FOR JAVA DEVELOPERS KOTLIN val game =

    VideoGame("Gears of War", "Epic Games", 8) ▸ Data classes are instantiated in the same way as standard classes:
  35. DATA CLASSES KOTLIN FOR JAVA DEVELOPERS KOTLIN val game =

    VideoGame("Gears of War", "Epic Games", 8) ▸ Data classes are instantiated in the same way as standard classes: ▸ We can now access the members of game: print(game.name) // "Gears of War" print(game.publisher) // "Epic Games" print(game.reviewScore) // 8 game.reviewScore = 7
  36. DATA CLASSES KOTLIN FOR JAVA DEVELOPERS KOTLIN ▸ We can

    pretty-print the contents of the class via toString(): /* Prints: * Game(name=Gears Of War, publisher=Epic Games, reviewScore=7) */ print(game.toString())
  37. DATA CLASSES KOTLIN FOR JAVA DEVELOPERS KOTLIN ▸ We can

    pretty-print the contents of the class via toString(): ▸ We can copy an object and specify new values for specific parameters: /* Prints: * Game(name=Gears Of War, publisher=Epic Games, reviewScore=7) */ print(game.toString()) val game = VideoGame("Gears of War", "Epic Games", 8) val betterGame = game.copy(reviewScore = 10)
  38. DATA CLASSES KOTLIN FOR JAVA DEVELOPERS package com.kotlinreference.samples.dataclasses; public class

    VideoGamePojo { private String name; private String publisher; private int reviewScore; public VideoGamePojo(String name, String publisher, int reviewScore) { this.name = name; this.publisher = publisher; this.reviewScore = reviewScore; } public String getName() { return name; } public void setName(String name) { this.name = name; } public String getPublisher() { return publisher; } public void setPublisher(String publisher) { this.publisher = publisher; } public int getReviewScore() { return reviewScore; } public void setReviewScore(int reviewScore) { this.reviewScore = reviewScore; } @Override public boolean equals(Object o) { if (this == o) return true; if (o == null || getClass() != o.getClass()) return false; VideoGamePojo that = (VideoGamePojo) o; if (reviewScore != that.reviewScore) return false; if (name != null ? !name.equals(that.name) : that.name != null) { return false; } return publisher != null ? publisher.equals(that.publisher) : that.publisher == null; } @Override public int hashCode() { int result = name != null ? name.hashCode() : 0; result = 31 * result + (publisher != null ? publisher.hashCode() : 0); result = 31 * result + reviewScore; return result; } @Override public String toString() { return "VideoGamePojo{" + "name='" + name + '\'' + ", publisher='" + publisher + '\'' + ", reviewScore=" + reviewScore + '}'; } } package com.kotlinreference.samples.dataclasses data class VideoGame(val name: String, val publisher: String, var reviewScore: Int) JAVA/KOTLIN
  39. WHEN KOTLIN FOR JAVA DEVELOPERS fun evaluateNumber(num: Int) { when

    (num) { 26 -> print("num is exactly 26") 41 -> print("num is exactly 41") in 0..10 -> print("num is in the range 0 - 10") else -> print("none of the above") } } KOTLIN ▸ Branching by value:
  40. WHEN KOTLIN FOR JAVA DEVELOPERS KOTLIN ▸ Branching by type:

    fun evaluateObject(obj: Any): String { return when (obj) { is String -> "obj is a String" is Int -> "obj is an Int" is Float -> "obj is a Float" else -> "obj is something else" } }
  41. WHEN KOTLIN FOR JAVA DEVELOPERS KOTLIN ▸ Branching with expressions:

    fun evaluateNumber(num: Int) { when { num.isEven() -> print("num is even") num.isOdd() -> print("num is odd") else -> { print("the universe is broken") } } }
  42. SMART CASTING KOTLIN FOR JAVA DEVELOPERS open class FeedItem class

    Tweet : FeedItem() class RedditPost : FeedItem() class DribbblePost : FeedItem() open class FeedScreen class TweetScreen(val tweet: Tweet) : FeedScreen() class RedditScreen(val redditPost: RedditPost) : FeedScreen() class DribbbleScreen(val dribbblePost: DribbblePost) : FeedScreen() KOTLIN
  43. SMART CASTING KOTLIN FOR JAVA DEVELOPERS public FeedScreen getScreenOnClick(FeedItem feedItem)

    { if (feedItem instanceof Tweet) { Tweet tweet = (Tweet) feedItem; return new TweetScreen(tweet); } else if (feedItem instanceof RedditPost) { RedditPost redditPost = (RedditPost) feedItem; return new RedditScreen(redditPost); } else if (feedItem instanceof DribbblePost) { DribbblePost dribbblePost = (DribbblePost) feedItem; return new DribbbleScreen(dribbblePost); } else { return null; } } JAVA
  44. SMART CASTING KOTLIN FOR JAVA DEVELOPERS fun getScreenOnClick(feedItem: FeedItem): FeedScreen?

    { return if (feedItem is Tweet) { TweetScreen(feedItem) } else if (feedItem is RedditPost) { RedditScreen(feedItem) } else if (feedItem is DribbblePost) { DribbbleScreen(feedItem) } else { null } } KOTLIN
  45. fun getScreenOnClick(feedItem: FeedItem): FeedScreen? { return if (feedItem is Tweet)

    { TweetScreen(feedItem) } else if (feedItem is RedditPost) { RedditScreen(feedItem) } else if (feedItem is DribbblePost) { RedditScreen(feedItem) } else { null } } SMART CASTING KOTLIN FOR JAVA DEVELOPERS KOTLIN
  46. SEALED CLASSES KOTLIN FOR JAVA DEVELOPERS public FeedScreen getScreenOnClick(FeedItem feedItem)

    { if (feedItem instanceof Tweet) { Tweet tweet = (Tweet) feedItem; return new TweetScreen(tweet); } else if (feedItem instanceof RedditPost) { RedditPost redditPost = (RedditPost) feedItem; return new RedditScreen(redditPost); } else if (feedItem instanceof DribbblePost) { DribbblePost dribbblePost = (DribbblePost) feedItem; return new DribbbleScreen(dribbblePost); } else { return null; // not meaningful! } } JAVA
  47. SEALED CLASSES KOTLIN FOR JAVA DEVELOPERS public FeedScreen getScreenOnClick(FeedItem feedItem)

    { if (feedItem instanceof Tweet) { Tweet tweet = (Tweet) feedItem; return new TweetScreen(tweet); } else if (feedItem instanceof RedditPost) { RedditPost redditPost = (RedditPost) feedItem; return new RedditScreen(redditPost); } else { // still not meaningful! DribbblePost dribbblePost = (DribbblePost) feedItem; return new DribbbleScreen(dribbblePost); } } JAVA
  48. SEALED CLASSES KOTLIN FOR JAVA DEVELOPERS open class FeedItem class

    Tweet : FeedItem() class RedditPost : FeedItem() class DribbblePost : FeedItem() open class FeedScreen class TweetScreen(val tweet: Tweet) : FeedScreen() class RedditScreen(val redditPost: RedditPost) : FeedScreen() class DribbbleScreen(val dribbblePost: DribbblePost) : FeedScreen() KOTLIN
  49. SEALED CLASSES KOTLIN FOR JAVA DEVELOPERS sealed class FeedItem {

    class Tweet : FeedItem() class RedditPost : FeedItem() class DribbblePost : FeedItem() } sealed class FeedScreen { class TweetScreen(val tweet: Tweet) : FeedScreen() class RedditScreen(val redditPost: RedditPost) : FeedScreen() class DribbbleScreen(val dribbblePost: DribbblePost) : FeedScreen() } KOTLIN
  50. SEALED CLASSES KOTLIN FOR JAVA DEVELOPERS fun getScreenOnClick(feedItem: FeedItem): FeedScreen

    { when (feedItem) { is Tweet -> return TweetScreen(feedItem) is RedditPost -> return RedditScreen(feedItem) is DribbblePost -> return DribbbleScreen(feedItem) } } KOTLIN
  51. SEALED CLASSES KOTLIN FOR JAVA DEVELOPERS fun getScreenOnClick(feedItem: FeedItem): FeedScreen

    { return when (feedItem) { is Tweet -> TweetScreen(feedItem) is RedditPost -> RedditScreen(feedItem) is DribbblePost -> DribbbleScreen(feedItem) } } KOTLIN
  52. SEALED CLASSES KOTLIN FOR JAVA DEVELOPERS fun getScreenOnClick(feedItem: FeedItem) =

    when (feedItem) { is Tweet -> TweetScreen(feedItem) is RedditPost -> RedditScreen(feedItem) is DribbblePost -> DribbbleScreen(feedItem) } KOTLIN
  53. RETURN/ASSIGN EVERYTHING KOTLIN FOR JAVA DEVELOPERS fun getScreenOnClick(feedItem: FeedItem) =

    when (feedItem) { is Tweet -> TweetScreen(feedItem) is RedditPost -> RedditScreen(feedItem) is DribbblePost -> DribbbleScreen(feedItem) } KOTLIN fun sum(first: Int = 2, second: Int) = first + second val fullName = if (surname != null) { "$firstName $surname" } else { firstName }
  54. WITH() KOTLIN FOR JAVA DEVELOPERS JAVA/KOTLIN ▸ ‘With’ is used

    when we are calling multiple methods on the same object. ▸ Acts as if we are ‘inside’ the objects’ scope. void printGame(VideoGame game) { print(game.getName()); print(game.getPublisher()); print(game.getReviewScore()); } fun printGame(game: VideoGame) = with(game) { print(name) print(publisher) print(reviewScore) }
  55. LET() KOTLIN FOR JAVA DEVELOPERS KOTLIN ▸ A scoping function

    which gives us access to an object inside the defined scope but not beyond. storageProvider.provideDatabase().let { database -> // database only available inside this scope } fun getGameByName(name: String?): VideoGame? { return name?.let { database.getGame(name) } } ▸ When combined with ‘?’, ‘let’ smart-casts your nullable field to a non-null field: ▸ Now non-nullable
  56. RUN() KOTLIN FOR JAVA DEVELOPERS KOTLIN fun printGame(game: VideoGame?) =

    game?.run { print(name) print(publisher) print(reviewScore) } ▸ ‘Run’ is a combination of ‘with’ and ‘let’. ▸ The null-check power of ‘let’ and the scoping of ‘with’.
  57. APPLY() KOTLIN FOR JAVA DEVELOPERS JAVA/KOTLIN public File makeFile() {

    File file = new File("path"); file.mkdirs(); file.setReadable(true); file.setWritable(false); return file; } fun makeFile() = File("path").apply { mkdirs() setReadable(true) setWritable(false) } ▸ ‘Apply’ defines an extension on all types. ▸ The object you call apply on is passed into the closure, where you can work on it, and then returns the same object.
  58. USE() KOTLIN FOR JAVA DEVELOPERS JAVA/KOTLIN Properties properties = new

    Properties(); try (FileInputStream stream = new FileInputStream("config.properties")) { properties.load(stream); } // 'stream' automatically closed val properties = Properties() FileInputStream("config.properties").use { properties.load(it) } // stream automatically closed ▸ Kotlin version of Java ‘try-with-resources’ (Java 1.7+)
  59. LAZILY-INITIALISED SINGLETONS KOTLIN FOR JAVA DEVELOPERS class MySingleton { private

    static MySingleton instance; @Nullable String myString = null; private MySingleton() {} static MySingleton getInstance() { if (instance == null) { instance = new MySingleton(); } return instance; } } MySingleton.getInstance().myString = "hello"; JAVA/KOTLIN
  60. LAZILY-INITIALISED SINGLETONS KOTLIN FOR JAVA DEVELOPERS object MySingleton { var

    myString: String? = null } MySingleton.myString = "hello" class MySingleton { private static MySingleton instance; @Nullable String myString = null; private MySingleton() {} static MySingleton getInstance() { if (instance == null) { instance = new MySingleton(); } return instance; } } MySingleton.getInstance().myString = "hello"; ▸ MySingleton is initialised at this point JAVA/KOTLIN
  61. COLLECTIONS KOTLIN FOR JAVA DEVELOPERS KOTLIN ▸ The Collections API

    - a library of functions which manipulate collections of data, e.g: ▸ Mapping ▸ Grouping ▸ Sorting ▸ Filtering ▸ Equivalent to Java 8 streams ▸ Much more fluent syntax ▸ Available on Java 6 (again, great for Android!)
  62. COLLECTIONS KOTLIN FOR JAVA DEVELOPERS KOTLIN val games = listOf(

    VideoGame("Gears of War", "Epic Games", 8), VideoGame("Bioshock", "2K Games", 8), VideoGame("Snake", "Nokia", 10)) val mutableGames = mutableListOf( VideoGame("Gears of War", "Epic Games", 8), VideoGame("Bioshock", "2K Games", 8), VideoGame("Snake", "Nokia", 10)) games.forEach { print(it.name) } games.forEachIndexed { index, videoGame -> print("$index - $videoGame") }
  63. COLLECTIONS KOTLIN FOR JAVA DEVELOPERS KOTLIN ▸ Return a list

    of items which match the predicate: val bestGames = games.filter { it.reviewScore == 10 }
  64. COLLECTIONS KOTLIN FOR JAVA DEVELOPERS KOTLIN ▸ Return a list

    of items which match the predicate: val bestGames = games.filter { it.reviewScore == 10 } ▸ Return a list of items which do not match the predicate: val worstGames = games.filterNot { it.reviewScore >= 5 }
  65. COLLECTIONS KOTLIN FOR JAVA DEVELOPERS KOTLIN ▸ Return a list

    of items which match the predicate: val bestGames = games.filter { it.reviewScore == 10 } ▸ Return a list of items which do not match the predicate: val worstGames = games.filterNot { it.reviewScore >= 5 } ▸ Return a list of items equal to the first or last n items: val firstTwoGames = games.take(2) val lastTwoGames = games.takeLast(2)
  66. COLLECTIONS KOTLIN FOR JAVA DEVELOPERS KOTLIN ▸ Return the number

    of items which match the predicate: val numOfTens: Int = games.count { it.reviewScore == 10 }
  67. COLLECTIONS KOTLIN FOR JAVA DEVELOPERS KOTLIN ▸ Return the number

    of items which match the predicate: ▸ Return ‘true’ if all items match the predicate: val numOfTens: Int = games.count { it.reviewScore == 10 } val allTens: Boolean = games.all { it.reviewScore == 10 }
  68. COLLECTIONS KOTLIN FOR JAVA DEVELOPERS KOTLIN ▸ Return the number

    of items which match the predicate: ▸ Return ‘true’ if all items match the predicate: ▸ Return ‘true’ if any items match the predicate: val numOfTens: Int = games.count { it.reviewScore == 10 } val allTens: Boolean = games.all { it.reviewScore == 10 } val anyTens: Boolean = games.any { it.reviewScore == 10 }
  69. COLLECTIONS KOTLIN FOR JAVA DEVELOPERS KOTLIN ▸ Return the number

    of items which match the predicate: ▸ Return ‘true’ if all items match the predicate: ▸ Return ‘true’ if any items match the predicate: val numOfTens: Int = games.count { it.reviewScore == 10 } val allTens: Boolean = games.all { it.reviewScore == 10 } val anyTens: Boolean = games.any { it.reviewScore == 10 } ▸ Return ‘true’ if no items match the predicate: val noTens: Boolean = games.none { it.reviewScore == 10 }
  70. COLLECTIONS KOTLIN FOR JAVA DEVELOPERS KOTLIN ▸ Return an item

    at the given index or the result of our defaultValue function if the index given is out of bounds: val gameOrElse = games.elementAtOrElse(0, { VideoGame("default", "default", 1) }) val combined = listOf(1, 2) + listOf(3, 4) ▸ Combine two lists:
  71. COLLECTIONS KOTLIN FOR JAVA DEVELOPERS KOTLIN ▸ Return the first

    item that matches the predicate or ‘null’ if no item was found: val firstOrNull: VideoGame? = games.find { it.name == "Bioshock" }
  72. COLLECTIONS KOTLIN FOR JAVA DEVELOPERS KOTLIN ▸ Returns the single

    element that matches the predicate or throws an exception if there is zero or more than one matching item: ▸ Return the first item that matches the predicate or ‘null’ if no item was found: val firstOrNull: VideoGame? = games.find { it.name == "Bioshock" } val singleGame = games.single { it.name == "Bioshock" }
  73. COLLECTIONS KOTLIN FOR JAVA DEVELOPERS KOTLIN ▸ Returns the single

    element that matches the predicate or throws an exception if there is zero or more than one matching item: ▸ Return the first item that matches the predicate or ‘null’ if no item was found: val firstOrNull: VideoGame? = games.find { it.name == "Bioshock" } val singleGame = games.single { it.name == "Bioshock" } ▸ Same as above but returns ‘null’ instead of throwing an exception: val singleOrNull = games.singleOrNull { it.name == "Bioshock" }
  74. COLLECTIONS KOTLIN FOR JAVA DEVELOPERS KOTLIN ▸ Apply the transform

    function to each item in the collection and return a list of the transformed items: val allScoresDeducted = games.map { it.copy(reviewScore = it.reviewScore - 2) }
  75. COLLECTIONS KOTLIN FOR JAVA DEVELOPERS KOTLIN ▸ Apply the transform

    function to each item in the collection and return a list of the transformed items: val allScoresDeducted = games.map { it.copy(reviewScore = it.reviewScore - 2) } ▸ Create a new collection for each item in the collection and then flatten them into a unique list containing all of the elements: val playerIds = games.flatMap { getListOfPlayersForGame(it) }
  76. COLLECTIONS KOTLIN FOR JAVA DEVELOPERS KOTLIN ▸ Group items according

    to the ‘keySelector’ function we pass as the parameter: val grouped: Map<String, List<VideoGame>> = games.groupBy { if (it.reviewScore > 6) "good" else "bad" }
  77. COLLECTIONS KOTLIN FOR JAVA DEVELOPERS KOTLIN ▸ Group items according

    to the ‘keySelector’ function we pass as the parameter: val alphabeticalAZ = games.sortedBy { it.name } val alphabeticalZA = games.sortedByDescending { it.name } ▸ Sort items according to the ‘selector’ function we pass as the parameter: val grouped: Map<String, List<VideoGame>> = games.groupBy { if (it.reviewScore > 6) "good" else "bad" }
  78. COLLECTIONS KOTLIN FOR JAVA DEVELOPERS KOTLIN ▸ We often combine

    these transformations ▸ Example: “Take the first 100 games, find which ones start with 'a' or 'b', give them a random review score, sort them by highest review score and show me the top 3.” games.take(100) .filter { it.name.startsWith("a") || it.name.startsWith("b") } .map { it.copy(reviewScore = random.nextInt()) } .sortedByDescending { it.reviewScore } .take(3)
  79. A PARADIGM SHIFT IN THINKING KOTLIN FOR JAVA DEVELOPERS KOTLIN

    ▸ Kotlin is an object-oriented language with functional constructs. ▸ Lets the developer choose how to use it: ▸ Object-Oriented Programming via classes and instances. ▸ Functional Programming via higher-order functions. ▸ A mix of both, Kotlin is a flexible, interoperable language. ▸ Learn to maintain readability while increasing conciseness.
  80. A PARADIGM SHIFT IN THINKING KOTLIN FOR JAVA DEVELOPERS KOTLIN

    ▸ My personal preference: ▸ Prefer to think in terms of data and functions, rather than objects - steer away from complex class hierarchies and explore the top- level. ▸ Compose functionality from functions - e.g. eliminate your mapper class. ▸ Prefer to write stateless code with clear inputs and outputs via functions over OOP which promotes mutability via objects. ▸ Still adhere to the more sensible OOP principles when possible. Kotlin will be part of a bigger Java eco-system for a while so look at the bigger picture.
  81. KOTLIN FOR JAVA DEVELOPERS BRINGING KOTLIN TO A BUSINESS ▸

    Barriers ▸ Initial learning curve - syntax/best practices/paradigm shift ▸ Change in perspective to functional programming ▸ Dex Limit on Android ▸ Benefits ▸ Increase code safety - NPE/ClassCastException ▸ Less code overall ▸ Interoperable with existing app code and Java libraries ▸ Increase developer productivity/happiness KOTLIN
  82. KOTLIN FOR JAVA DEVELOPERS BRINGING KOTLIN TO A JAVA TEAM

    ▸ My situation: ▸ Current team: ~6 Java developers ▸ Start with 1 or 2 developers using Kotlin ▸ How to introduce Kotlin: ▸ Use Kotlin in an isolated component ▸ Involve other developers in code reviews ▸ Workshops/Codelabs ▸ Listen to IntelliJ suggestions! KOTLIN
  83. KOTLIN FOR JAVA DEVELOPERS USEFUL LINKS ▸ Kotlin Koans: http://try.kotlinlang.org

    ▸ Install Kotlin with Gradle: https://medium.com/@CodingDoug/ kotlin-android-a-brass-tacks-experiment-part-1-3e5028491bcc ▸ Compilation Speeds: https://medium.com/keepsafe-engineering/ kotlin-vs-java-compilation-speed-e6c174b39b5d ▸ Collection operations: https://antonioleiva.com/collection- operations-kotlin ▸ Standard library: http://beust.com/weblog/2015/10/30/ exploring-the-kotlin-standard-library/ KOTLIN
  84. KOTLIN FOR JAVA DEVELOPERS MORE KOTLIN TALKS ▸ Introduction to

    Kotlin (Google I/O ’17): https:// www.youtube.com/watch?v=X1RVYt2QKQE ▸ Android Development with Kotlin (Jake Wharton): https:// www.youtube.com/watch?v=A2LukgT2mKc ▸ Kotlin in Production (Droidcon NYC ’16): https:// www.youtube.com/watch?v=mDpnc45WwlI ▸ Life is Great and Everything Will Be Ok, Kotlin is Here (Google I/O ’17): https://www.youtube.com/watch?v=fPzxfeDJDzY KOTLIN