Kotlin
- Kotlin is a statically typed programming language
- Officially supported language by Google for android
Core features of Kotlin:
- Concise: Reduces the amount of boilerplate code
- Safe: Avoid NullPointerException
- Interoperable: Use existing libraries of Java, Android, etc
- Tool friendly: Use any existing IDE
Hello world!
fun main() {
println("Hello world!")
}
Variables
...
val a = "Hello" //type inference
val a: Double = 23.44
...
val vs var
- val is value and var is variable
- val is nothing but a final value(like Java) which can not be reassigned.
- var can be reassigned.
- Can not change the type of a var. It is bounded by its defined type.
- We can use lateinit to initialise var later.
...
lateinit var a: String;
...
a = "Aditya"
...
- We can not set a null value to a var. We need to use ? operator. This is due to strong null safety check which comes attached with Kotlin.
...
var a: String? = null;
...
- To get a NPE for a var in Kotlin, we need to use !! operator. It makes sure that we receive NPE if it occurs.
...
var a: String? = null
...
val size: Int = a?.length!! //throws NPE
- We have and elvis operator in Kotlin which is similar to conditional operator. (?:)
...
var a: String? = null
...
val size: Int = a?.length ?: 0 //returns 0 if a.length is null
- If we need to concatenate a string to another, there is a smart way to do it in kotlin
...
var a: String = "Aditya"
println(a + "Singh") //prints Aditya Singh
println("$a Singh") //prints Aditya Singh
...
Arrays
- We can define array in following ways:
val a = arrayOf(1,2,3,4,"Aditya")
/*
arrayOf() uses vararg underneath which tells that we can have n arguements
inside a function.
*/
val a = arrayOf<Int>(1,2,3,4)
/*
This will bind our array with Int type. We cant add any other variable of any
other type inside it.
*/
val num = Array(5, {i -> i*1}) //0 1 2 3 4
/*
Using Array constructor
*/
println(a[3])
println(a.get(3))
Collections
- By default in kotlin list is immutable
...
val myList = listOf<String>("Hello","World","Aditya")
...
myList.add("India") //cant do that as there is no function add()
- If we want to add items we need to explicitly define it as mutable. We can use arrayListOf() also in place of mutableListOf().
...
val myList = mutableListOf<String>("Hello","World")
...
myList.add("Aditya")
- Maps are immutable.
...
val myMap = mapOf<Int,String>(1 to "Aditya", 2 to "Singh")
...
println(myMap[1]) //this will print "Aditya"
val myMap = mapOf(1 to "Aditya", "surname" to "Singh") //to use different keys
- If we want mutable map, we use hash map.
...
val myMap = hashMapOf(1 to "Aditya", "surname" to "Singh")
...
myMap.set("country", "India") //add a new key value pair
myMap["country"] = "India" //we can do something like this as well
Loops
- Foreach loops works with list, array, map. It iterates over the entire set of items and give the output.
val myList = listOf<String>("Hello","World","Aditya")
myList.forEach(it -> println(it)) //prints all items
- for loop
for (name in listOfNames) {
println(name) //print every item in list
}
for ( x in 0..10) {
println(x) //prints all value from 0 to 10 inclusive
}
for ( x in 0 until 10) {
println(x) //prints all value from 0 to 10, excludes 10
}
for ( x in 0 until 10 step 3) {
println(x) //prints 0 3 6 9
}
for ( x in 10 downTo 0 step 3) {
println(x) //prints 10 7 4 1
}
Keywords
inis check inclusiveness
When
- It is similar to switch statement of C++. We dont iterate over all the condition like we do in if-else.
...
var a:String = "Aditya"
when(a) {
"Aditya" -> {
println("Aditya") //will print this
}
"Singh" -> {
println("Singh")
}
else {
println("Other")
}
}
...
- When can return a value as well.
Functions
- The structure of functions is very similar to C++ or Java.
fun functionName(variable: Int): String {
return "$variable was passed"
}
Types of arguements:
- Positional arguments: Arguments are passed in the order they are declared in the function definitions
- Default arguments: There can be default values defined as an argument. We can choose not to pass it as a parameter. Function will pick up the default value.
- Named arguments: These are special in kotlin. We can send parameter in any order, just specifying the name
... callFun(name="Aditya", age=22, company="Amazon") fun callFun(name: String, age: Int, company: String) { //do something }If we are not sure of number of argument to pass, we can use vararg.
...
callFunction(1,2,3,4)
fun callFunction(vararg number: Int) {
println(number.size)
for(num in number) {
prinln(num)
}
}
...
Class
- Similar to classes in C++
class User {
var name: String = "Aditya"
var age: Int = 22
fun getAge(): Int {
return age
}
fun assignValue(name:String, age: Int) {
this.name = name
this.age = age
}
}
- this keyword is used to access members of current class. It points to the current class present in scope.
- Constructor are used to initialise the members of a class. There are 2 types of constructors:
- Primary constructor (We can have only one primary constructor in a class)
- Secondary constructor (We can have multiple secondary constructor in a class
class User(var name: String, var age: Int) {
var name: String
var age: Int
fun getAge(): Int {
return age
}
fun assignValue(name:String, age: Int) {
this.name = name
this.age = age
}
}
...
val user = User("Aditya", 22)
- We can use init block as well as a constructor
class User(name: String, age: Int) {
var name: String
var age: Int
init {
name = name
age = age
}
fun getAge(): Int {
return age
}
fun assignValue(name:String, age: Int) {
this.name = name
this.age = age
}
}
- There can be multiple secondary constructor.
class User(name: String, age: Int) {
var name: String
var age: Int
constructor(name: String) {
this.name = name
age = 22
}
constructor(name: String, age: Int) {
this.name = name
this.age = age
}
}
Kotlin Java interoperability
- Kotlin is compiled as Java when present in backend java project.
- We can see the equivalent java code by following procedure:
- We need to check the kotlin bytecode i.e. the code which machine understands
- We can decompile the bytecode, which reverse engineers it java (source does’nt matter)
- No need to add getter and setter in kotlin, it automatically does that for us.
