Programmingバックエンド開発者

Kotlinにおける数値範囲のメカニズムを説明してください:RangeとProgressionはどのように機能し、独自の範囲を作成する方法と、それらを便利に適用するシナリオはどのようなものですか?

Hintsage AIアシスタントで面接を突破

答え

問題の歴史

Kotlinでは、最初から数値の連続したセットとの操作を簡素化するために範囲(Range)が導入されました。これは、数値の操作時に簡潔な構文を持つ言語(たとえば、Python)から継承されたものです。さらに、RangeのメカニズムはProgressionに拡張され、反復のステップを設定し、さまざまなタイプの数値や文字をサポートできるようになりました。

問題

整数、文字、時間点などを反復する際は、特別な構文と標準ライブラリによる信頼できるサポートがしばしば必要であり、そうでない場合、コードは冗長になり、可読性が低下し、境界に関するエラーが生じやすくなります。

解決策

Kotlinには、標準のIntRange、CharRange、LongRangeがあり、また、ステップ反復用のProgressionもあります。さらに、任意のComparable型の範囲を定義することもできます。

// 単純な範囲 for (i in 1..5) print(i) // 12345 // ステップ付き範囲 for (i in 1..10 step 2) print(i) // 13579 // 逆範囲 for (i in 5 downTo 1) print(i) // 54321 // 独自の範囲(例:Versionのため) data class Version(val major: Int, val minor: Int): Comparable<Version> { override fun compareTo(other: Version): Int = compareValuesBy(this, other, Version::major, Version::minor) } operator fun ClosedRange<Version>.iterator(): Iterator<Version> = object : Iterator<Version> { var current = start override fun hasNext() = current <= endInclusive override fun next() = current.also { current = Version(current.major, current.minor + 1) } } val v1 = Version(1, 0) val v2 = Version(1, 3) for (v in v1..v2) println(v)

主な特徴:

  • 標準の範囲構文: .., downTo, until, step
  • 数値、文字、ユーザー定義型の操作
  • ループ、メンバーシップチェック、分割、バリデーションへの適用

ワナの質問

1..51 until 5 の違いは何ですか?

1..5は範囲の両端を含みます:1,2,3,4,5。1 until 5は最後の要素を含みません:1,2,3,4。

ステップを使用して0未満のステップの範囲を設定できますか?

いいえ。減少する範囲にはdownTo構造を使用し、その後にステップを設定します:5 downTo 1 step 2(5,3,1を得ます)。

Comparableを実装していない型で範囲を使用できますか?

いいえ。範囲を作成するためには、型が比較をサポートしている必要があります。そうでない場合、コンパイラは定義を許可しません。

一般的なエラーとアンチパターン

  • ..ではなくuntilを使用する、あるいはその逆、境界の包含に混乱
  • 増加する範囲に対して負のステップを設定する(ステップは逆の範囲を作成しません)
  • ユーザー定義型の範囲に対してComparableの要件を守らない

実生活の例

悪いケース

コードで1 until n+1の代わりに1..nを使用しました。余分な要素が得られ、ループが範囲の境界を越えます。

利点:

  • 意図せず端数ケースをキャッチ

欠点:

  • 境界での分割エラー、不正確な合計計算

良いケース

配列の長さnに対するインデックス付けにfor (i in 0 until n)を使用しています。範囲は有効なインデックス値と厳密に一致します。

利点:

  • 配列の境界を越えるエラーを排除
  • 可読性が向上

欠点:

  • 言語間の遷移時に..untilの違いを覚えておく必要があります。