# Kotlin
[Udemy Course](https://deliveryhero.udemy.com/course/kotlin-for-java-developers/learn/lecture/7792652#overview)
[Blog](https://www.educative.io/blog/kotlin-tutorial-for-java-developers)
## Kotlin features
**Static Typing:** Like Java, variables can only be assigned values that match their type.
```
var m : Int = 12
m = 10 // ok
m = "twelve" // error!
m = 10.0 // error!
```
**Non-local jumps:** Kotlin allows you to exit a function anywhere
```
fun main() {
intArrayOf(4, 5, 6).forEach lambda@ {
if (it == 5) return@lambda
println(it)
}
loop@ for (i in 0 .. 3) {
for (j in 0 .. 3) {
if (i + j == 4) continue@loop
if (i + j == 5) break@loop
println(i + j)
}
}
}
```
**Collection filtering:** Allows you to search collections for any data that matches the passed criteria.
```
val languageArray = arrayOf("Serbian", "Swahili", "Japanese", "German", "Spanish")
val selectedLang = languageArray
.filter { name -> name.startsWith("s", ignoreCase = true) }
//or: .filter { it.startsWith("s", ignoreCase = true) }
.sortedBy { name -> name.length }
.first()
```
**Extension functions:** Extension functions allow you to extend existing components without writing methods inside them, leading to cleaner code.
```
class Person {
var firstName = ...
var lastName = ...
}
// Maybe the author of the Person class forgot to include this
fun Person.setName(firstName: String, lastName: String) {
this.firstName = firstName
this.lastName = lastName
}
```
**Higher-order functions:** Kotlin functions are treated as first-class, meaning they can be passed or returned from other functions.
```
people.filter { person -> person.headCount == 1 }
```
**Lazy loading:** Decreases loading time by only loading resources it’ll immediately need.
## Variables Declaration
```
var <variableName> = <value> //mutable
val <variableName> = <value> //read-only
val <variableName>: <dataType> = <value> // explicit type casting
```
- Kotlin allows for smart typing, sometimes called implicit typing, where it **automatically detects the data type** of a variable without explicit tagging.
- Kotlin **does not allow you to assign a null value to variables or return values by default**. With Java, you can assign null, but it will throw a nullPointerException if you try to access that value.
### Read-only vs Mutable variables
Variables in Kotlin can be either **read-only** or **mutable**. The value of **read-only** variables cannot be changed after they’ve been initially assigned.
```
val number = 17
println("number = $number")
number = 42 // Not allowed, throws an exception
var number = 17
println("number = $number")
number = 42 // var can be reassigned
println("number = $number")
```
It’s **best practice to use read-only val variables whenever possible** and only use mutable var when you specifically need it. This minimizes the overall complexity of your programs and makes it easier to understand their data flow.
## Kotlin Data Types
Unlike Java, Kotlin **does not have primitive data types**. All the following types are objects at runtime but do transpile to the respective Java primitive types in Java bytecode.
```
//INTEGER TYPES
val byte: Byte = 127
val short: Short = 32767
val int: Int = 2147483647
val long: Long = 9223372036854775807
// FLOAT AND DOUBLE behave the same,
but Double can hold more numbers than Float.
val float: Float = 3.4028235e38f
val double: Double = 1.7976931348623157e308
// STRINGS. You denote single characters with single quotes,'c',
and Strings with double quotes “this string”`.
val character: Char = '#'
val text: String = "Learning about Kotlin's data types"
// BOOLEANS
val yes: Boolean = true
val no: Boolean = false
```
**Type inference**
Allows you to omit types in your code when the compiler can infer it for you. This is also sometimes called **smart typing** or **implicit typing**.
If a variable could be declared as two types of differing sizes, it will choose the default: Double for floating-point numbers and Int for integers.
```
val string = "Educative"
val int = 27
```
## Conditionals and Loops
### If statement
```
var max = a
if (a < b) max = b
var max: Int
if (a > b) {
max = a
} else {
max = b
}
// As expression
val max = if (a > b) a else b
```
### When Statement
```
when (x) {
1 -> print("x == 1") //branch 1
2 -> print("x == 2") //branch 2
else -> { // Note the block
print("x is neither 1 nor 2")
}
}
```
### For Loop
The Kotlin for loop works like a C for each loop rather than Java’s for loop. It accepts a collection, like an array, and completes the same action on each element of the collection.
```
for (item in collection) print(item)
for (i in 1..3) {
println(i)
}
```
### While Loop
The while loop executes the body of code repeatedly so long as the listed conditions remain met. Like Java, there are two types of while loop. The **standard while loop** checks for the condition before the code is executed, and the **do-while loop** checks after the code is executed.
```
// regular why loop
while (x > 0) {
x--
}
// do while..
do {
val y = retrieveData()
}
while (y != null) // y is visible here!
```
## Kotlin Collections
## Kotlin Functions
### Extension Functions
## Functional Programming with Kotlin