繼續學習 Kotin,本篇筆記會紀錄 Functions
主要特性
- 不需要存活在 Class 內
- 使用
fun
關鍵字 - 參數可以設定預設值
- 可以使用 named parameters
- 可以擴充既有 types
筆記
-
Function 宣告
1
2
3
4fun display(message: String): Boolean {
....
return true
}: String
宣告變數或回傳型別為何
-
支援 Expessions 型態
1
val message = if(a>b) "a" else "b"
-
如何在 Java 內呼叫 Function
1
2
3
4
5
6package com.cky
// Util.kt 檔案
fun display(message: String): Boolean {
println("Hello $message")
return true
}編譯後,Java 會看成這樣,之後就跟使用其他 static function 的方法是一樣的
1
2
3
4
5
6
7
8
9
10
11// class UtilKt() {
// static boolean display(String message) { ... }
// }
import com.cky.UtilKt;
public class App {
public static void main(String[] args) {
UtilKt.display("Hello");
}
}可以透過
@file:JvmName("SomeClassName")
的方式來改變 Jvm 看 Kotlin function 的方式1
2
3
4
5
6
7"SomeClassName") (
package com.cky
fun display(message: String): Boolean {
println("Hello $message")
return true
}會轉換成
1
2
3
4
5
6
7
8
9
10
11// class SomeClassName {
// static boolean display(String message) { ... }
// }
import com.cky.SomeClassName;
public class App {
public static void main(String[] args) {
SomeClassName.display("Hello");
}
} -
Default Parameters 在 C# 或是其他語言已經存在一段時間,但在 Java 並沒有這樣的觀念,而 Kotlin 的 Function 是可以設定預設值的
1
2
3
4
5
6
7
8
9fun display(message: String = "World"): Boolean {
println("Hello $message")
return true
}
fun main() {
display() // 顯示 Hello world
display("Kevin") // 顯示 Hello Kevin
} -
因為 Java 沒有 Defatul Parameters 的觀念,所以當上面的 function 要在 Java 中使用,有兩種方式,
- 有多少參數傳就傳多少
- 加上
@JvmOverloads
1
2
3
4
5
fun display(message: String = "World"): Boolean {
println("Hello $message")
return true
} -
Named Parameters,這一個觀念在其他語言也有存在, 正常在傳參數的時候,都是依 function 設計時的順序傳,而 Named Parameters 時,就可以使用指定名稱的方式傳
1
2
3
4
5
6
7
8fun display(message: String = "World", logLevel: Int = 1): Boolean {
println("Hello $message")
return true
}
fun main() {
display(logLevel = 2, message = "Kevin")
}- Named Parameters 不能和 Position Parameters 混用
- Named Parameters 順序不重要
- Java 呼叫時,不能使用指定名稱傳值
-
Extension Functions 的概念也存在於 C# 中,可以讓我們針對既有 Types / classes 擴充功能,例如:
"abc".myCustomFunction()
1
2
3
4
5
6
7fun String.hello(): String {
return "Hello $this"
}
fun main() {
println("Kevin".hello()) // Hello Kevin
}- line2: this 表示此 extension function 所接收到的值,以此範例就是 line 6 的
"Kevin"
- line2: this 表示此 extension function 所接收到的值,以此範例就是 line 6 的
-
Infix Functions
- Member or extension function
- Have a single parameter
- Marked with infix keyword
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29// 沒有使用 infix
fun main() {
val h1 = Header("H1")
val h2 = Header("H2")
val h3 = h1.plus(h2)
println(h3.Name) //H1H2
}
class Header(var Name: String) {}
fun Header.plus(other: Header): Header {
return Header(this.Name + other.Name)
}
// 使用 infix
fun main() {
val h1 = Header("H1")
val h2 = Header("H2")
val h3 = h1 plus h2 // <= 主要差異
println(h3.Name) //H1H2
}
class Header(var Name: String) {}
infix fun Header.plus(other: Header): Header {
return Header(this.Name + other.Name)
} -
可以透過 infix 來 overloading operators (不建議大量使用)
1
2
3
4
5
6
7
8
9
10
11infix operator fun Header.plus(other: Header): Header {
return Header(this.Name + other.Name)
}
fun main() {
val h1 = Header("H1")
val h2 = Header("H2")
val h3 = h1 + h2 // 可以使用 + operator
println(h3.Name) //H1H2
} -
Tail Recursive Functions
- 使用
tailrec
keyword - 必須要是正確型態 (corret form)
- 符合上面的條件,Kotlin 就會優化 Recursive Functions
- 使用
參考資料
- Kotlin Fundamentals | Plurasight