KotlinのRegexクラスのfindメソッドとmatchEntireメソッドの違い

KotlinのRegexクラスのfindメソッドとmatchEntireメソッドはどちらも正規表現にマッチするかを確認しMatchResultを返すが、以下のとおり挙動が異なる。

  • findメソッド: 正規表現が文字列の一部にマッチするかを確認しMatchResultを返す
  • matchEntireメソッド: 正規表現が文字列全体にマッチするかを確認しMatchResultを返す

例えば"123,456"というカンマで区切られた文字列に対してfindメソッドを使った場合は\\d+という正規表現は"123"にマッチする。

val regex = "\\d+".toRegex()
val result = regex.find("123,456")
println(result?.value) // 123

一方同じ文字列に対してmatchEntireメソッドを使った場合は\\d+という正規表現は"123,456"にマッチしない。

val regex = "\\d+".toRegex()
val result = regex.matchEntire("123,456")
println(result?.value) // null

matchEntireメソッドで全体にマッチさせつつ一部を取り出したい場合はグループ(カッコ()で囲う)を使う。

val regex = "^(\\d+),.*".toRegex()
val result = regex.find("123,456")
println(result?.groups?.get(1)?.value) // 123

Kotlinの正規表現

Regexクラス

Kotlinで正規表現を扱うにはRegexクラスを使う。

Regexクラスのインスタンスを作成するにはコンストラクタの引数に正規表現を渡す。
例えば数字のみの文字列をマッチさせる正規表現は以下のようになる。

val regex = Regex("\\d+")

また文字列のインスタンスメソッドでtoRegexメソッドでもRegexクラスのインスタンスを作成できる。

val regex = "\\d+".toRegex()

グループ化

正規表現でグループ化するには()で囲む。

例えばカンマ区切りの先頭の文字列(例えば “123,456” の “123”)を表すグループ化は以下のようになる。

val regex =  "^([^,]*),".toRegex()

グループで抽出する場合のfindとmatchEntireの違い

findメソッドの場合は部分的にマッチする正規表現を記述すればよい。

例えばカンマ区切りの先頭の文字列(例えば “123,456” の “123”)を取得するには^([^,]*),のような最初のカンマまでの正規表現でも抽出できる。

val regex = "^([^,]*),".toRegex()
val result = regex.find("123,456")
println(result?.groups?.get(1)?.value) // 123

一方matchEntireメソッドの場合は正規表現が文字列の全体にマッチする必要があるので、 例えば末尾に.*をつけるなどして^([^,]*),.*のように最後までの正規表現を記述する必要がある。

val regex = "^([^,]*),.*".toRegex()
val result = regex.matchEntire("123,456")
println(result?.groups?.get(1)?.value) // 123