はじめに
その2の続きです。関数について書きます。
スタンダードなやつ
スタンダードな関数の書き方は下記
1 2 3 4 |
fun 関数名(引数名: 引数の型): 戻り値型 { // なんか処理 return 戻り値 } |
こんな感じ
1 2 3 4 5 6 |
fun add(num1: Int, num2: Int): Int { return num1 + num2 } // 呼び出し add(1, 2) |
戻り値がUnitの関数
戻り値が Unit の場合、戻り値は省略できる。
1 2 3 4 5 6 7 8 9 |
fun printText(text: String): Unit { print(text) return Unit } // 戻り値省略可 fun printText(text: String) { print(text) } |
単一式関数
上述の add
関数のように1つの式だけからなる関数は下記のような単一式関数(Single-Expressopm function)として書ける。
1 2 3 4 |
fun add(num1: Int, num2: Int): Int = num1 + num2 // 戻り値は型推論で省略可 fun add(num1: Int, num2: Int) = num1 + num2 |
デフォルト引数
Swift と同じようにデフォルト引数を設定できる。
1 2 3 4 5 6 7 8 9 10 |
fun printText(text1: String = "Hello", text2: String = "World") { print(text1 + " " + text2) } printText() // Hello World printText("hoge", "piyo") // hoge piyo // 名前付き引数 printText(text2 = "piyo", text1 = "hoge") // hoge piyo printText(text2 = "piyo") // Hello piyo |
可長変引数
引数に vararg
をつけることで可長変引数を使える。1つの関数につき1つの可長変引数しか持たすことはできない。可長変引数以外にも引数がある場合は最後の引数を可長変引数にする。
1 2 3 4 5 6 7 8 9 |
fun sum(vararg nums: Int): Int { var value = 0 for (num in nums) { value += num } return value } sum(1, 2, 3) // 6 |
ローカル関数
関数の中に関数を定義できる。
1 2 3 4 5 6 |
fun hoge() { // ... fun piyo() { // ... } } |
ジェネリック関数
関数名の前に <>
を使用して、ジェネリックパラメータを持つことができる。
1 2 3 |
fun <T> singletonList(item: T): List<T> { // ... } |
関数オブジェクト
下記のように関数は変数に代入できる。関数の参照は ::
を使う。
1 2 3 4 5 6 |
fun add(num1: Int, num2: Int): Int { return num1 + num2 } val addFunc = ::add addFunc(1, 2) // 3 |
下記のように無名関数も作成できる。
1 2 |
val addFunc = fun (num1: Int, num2: Int) = num1 + num2 addFunc(1, 2) // 3 |
ラムダ式
Swift でいうクロージャ式だと思う。
1 2 3 4 5 6 7 8 9 10 11 12 13 |
val sum = { x: Int, y: Int -> x + y } // 型省略 val sum: (Int, Int) -> Int = { x, y -> x + y } // 呼び出し sum(1, 2) // 3 // 引数1つの場合はitで宣言される val even: (Int) -> Boolean = { it % 2 == 0 } // 呼び出し even(2) // true |
インライン関数
高階関数(引数や戻り値が関数型の関数)のオーバーヘッドを避けるために inline
修飾子というのがある。
1 2 3 |
inline fun lock<T>(lock: Lock, body: () -> T): T { // ... } |
正直ほぼ意味がわかってない。。。
リファレンスをどうぞ
拡張関数
Swift でいう extension。
1 |
fun Int.isEven() = this % 2 == 0 |
変数も拡張できる。
1 2 |
val Int.piyo: String get() = "piyo" |
中置記法
関数が下記の条件を満たす場合、中置記法が使える。
- 拡張関数である
- 引数が1つである
infix
が付いている
1 2 3 4 5 |
infix fun Int.plus(x: Int): Int { return this + x } 1 plus 2 // 3 |
あんま使い所わからないけど Map
初期化時の to
はこれかもしれない。
末尾再帰関数
再帰関数に tailrec
修飾子を付けるといい感じに最適化してくれるらしい。
1 2 |
tailrec fun findFixPoint(x: Double = 1.0): Double = if (x == Math.cos(x)) x else findFixPoint(Math.cos(x)) |
詳細はここのリファレンス
さいごに
あとはクラスについて書いたら Kotlin については終わりたい。(早くAndroidに。。。)
書いてからすごいまとめられた記事をみつけた。
Kotlin文法 - 関数とラムダ
コメント
[…] その3の続きです。クラスについて書きます。 […]