Kotlin is a (relatively) new statically typed language developed by Jetbrains, IntelliJ idea anyone?
Open-sourced at 2011 and Kotlin 1.0 released on February 15th 2016.
although widely used by JetBrains developers, Kotlin's big break was on Google I/O 2017 where Kotlin was announced as an official language for android development.
Some of Kotlin's key features are:
Concise, Safe, Interoperable & mature.
Kotlin is 100% interoperable with Java and you can use it with your current project without any problems, you can call Java code from Kotlin and vice versa, all you need to do is add a small plugin and you're all set.
Kotlin adds lots of modern features that organizations stuck with Java 7 or 8 or Android developers surely miss and one of its big advantages is that it solves the nullability problem.
Kotlin has a place in any of today's development environments, Kotlin/JVM for Android, backend & everything else that runs on the JVM, Kotlin/JS for frontend developers and Kotlin/Native for iOS, MacOS, Windows, Linux, WebAssembly & Android (again).
let's dive right in
VARIABLES
in Kotlin we declare variables like this:
val is a read only (immutable) variable that we must initialize at declaration and we can't change its value.
val name: String = "nir"
The compiler is smart enough to infer the type and we can declare it like this
val name = "nir"
var is a mutable variable
var lastName: String = "golan"
As in val we can remove the type and our code will run just fine
var lastName = "golan"
Variables declared with the var keyword can be change at a later time
lastName = "golanster"
but we can't change the type, so:
lastName = 123
will not compile.
CLASSES
Classes in kotlin are declared with the class keyword
class Person constructor(val firstName: String, var lastName: String)
As in the variable declaration where we could omit the type, here we can omit the constructor
class Person (val firstName: String, var lastName: String)
When we use the val keyword in the constructor, we declare and assign the class properties.
Another important class keyword is data, when we add the data keyword in front of the class we get getters, setters (for var and not for val) & toString, hashCode, equals & copy overrides.
Object & Class Instantiation
In Kotlin we instantiate objects & classes like this:
val person = Person("nir", "golan")
Notice we don't use the new keyword
Functions
Functions in Kotlin are declared with the fun keyword
fun sum(first: Int, second: Int) {}
If the function have a return value we add the return type after the ()
fun sum(first: Int, second: Int): Int {}
and in the {} we define the body of the function
if & when
In kotlin if & when are expressions and have a return value, so in our function we can write
fun sum(first: Int, second: Int): Int {
if (first > second) {
first
} else {
second
}
}
In Kotlin we also have default values & named parameters in functions
fun sum(first: Int = 5, second: Int = 10): Int {
if (first > second) {
first
} else {
second
}
}
We can call the function like this:
val number = sum(5,10) //normal call
val number = sum(first = 5, second = 10) //named parameters
val number = sum(second = 5, first = 10) //with named parameters we can
//call them in any order we want
val number = sum(second = 22) //with default values we can omit
//any parameter and call just the one we need
And because Kotlin is a concise language we can omit some {} and get this
fun sum(first: Int, second: Int) = if (first > second) first else second
And this is the closest thing we have to a ternary operator in Kotlin.
In Kotlin when is a switch statement on steroids, it can be used as a normal switch statement, but because it's also an expression that returns a value when used like that, we must add an else clause
fun whatAmI(value: Any?) = when(value) {
3 -> "value is exactly 3"
is Int -> "double the value = ${value * 2}"
"What the fuck?" -> "Swich case + if statement!"
else -> "No value"
}
In Kotlin everything inherits from Any, just like Object in Java
In the above use case we evaluate value, we declare the value of value and based on the value of value we return the value :-)
Extension Function
We can extend any Kotlin class with a function of our own, in fact, Kotlin itself is an Extension functions over Java.
Let's take Int for example
fun Int.maxValue(other: Int) = if (this > other) this else other
Here we define an extension function for Int where we pass in another value and return the bigger one
val max = 3.maxValue(4) // returns 4
We can add the keyword infix in front of the function thus making the syntax a bit more friendly
infix fun Int.maxValue(other: Int) = if (this > other) this else other
val max = 3 maxValue 4
Null Safty
First, let's see how NPE or null pointer exception can happen in Java
String luckyNumber = "7";
System.out.println(luckyNumber.length());
luckyNumber = null;
System.out.println(luckyNumber.length());
Here, when our program will reach the last line it will throw a java.lang.NullPointerException
, now lets see how Kotlin can help us with it.
In Kotlin a variable can't be null, if we declare a variable like we did before
var name: String = null
our program will not compile and we will get this message: null can not be a value of a non-null type String
In order for us to use null in Kotlin we must declare a support for null in the type
var name: String? = null
The ? in the end of the type tells the compiler that name
can be null, if in the declaration we omit the type the compiler will infer the type as String?
When using nullable variables we have safe & unsafe ways to deal with them.
First, let's take a look at the safe way,
name?.length()
The ? will check if the variable is null or not and only if its not null will execute the length()
method
name!!.length()
With !! we're telling the compiler: "I know this can be null, trust me, i know what i'm doing".
I don't have to tell you that this is the best way to get a NullPointerException, right?
If we need to have a value returned even if the variable is null, we can use the elvis operator, which returns what's right of it if the left side is null
val res = name?.length() ?: 0
Collections
In Kotlin we have all the basic collections: list, array, map, set, hashMap, hashSet, etc..
Lets see some ways we can manipulate them.
val list = 1..100 // declaration of a list with the numbers 1 to 100
list.map { it * 2 } //map iterates over the list and **it**
//is the value currently being evaluated
.filter { v -> v % 2 == 0 } //filter out the results that are odd
Now let's say that we have a list of 1000000000000000 elements, this could take time even on the latest system, and for the sake of the argument let's say we need to pass the list to a web page for it to display.
We can't let the user wait several minutes until they see some info on the screen, this is where asSequence comes in
val list = 1..1999999999999900
list.asSequence
.map { it * 2 }
.filter { v -> v % 2 == 0 }
list.forEach{print(it)} //extension function that iterate over the list
//and print the current value
asSequence
evaluates the list as lazy and every time a new value is added it's being printed.
That's all for now, Kotlin is a very exciting language with many more topics to cover and i will add more in the next few days.
Happy coding.
Top comments (0)