Kotlinの列挙型(enum class)は、制限された値のセットを宣言し、それにメソッドやプロパティを拡張することを可能にします。
enum class Direction { NORTH, SOUTH, WEST, EAST }
enumの要素はシングルトンであり、対応するサブタイプのインスタンスです。enum class Color(val rgb: Int) { RED(0xFF0000), GREEN(0x00FF00), BLUE(0x0000FF); fun containsRed() = (rgb and 0xFF0000 != 0) }
Color.RED.name)、インデックス(ordinal)でアクセスでき、values()で全リストを取得できます。==(同一性)で比較されます。要素はユニークです。Kotlinのenumクラス内に抽象メソッドを定義し、Javaのように各要素がその実装をオーバーライドすることはできますか?
正しい答え: はい、enumスタイルで抽象メソッドを宣言でき、各要素は自分の実装を提供する必要があります!
enum class State { START { override fun next() = RUNNING }, RUNNING { override fun next() = STOPPED }, STOPPED { override fun next() = STOPPED }; abstract fun next(): State }
事例
JavaからKotlinへの移行中、チームは新しいenumクラスを通常のクラスのように継承しようとしましたが、enumは継承できないことが判明し、アーキテクチャが破損しました。状態機械のモジュール性アプローチを完全に変更する必要がありました。
事例
データベースに値を保存するために要素名(
enum.name)を使用しましたが、リファクタリングでenumの要素名が変更されたため、データベースのデータが新しいロジックに一致しなくなり、一貫性が失われました(ストレージ値パターンが実装されていなかった)。
事例
Gsonを介してenumクラスをシリアル化する際、カスタムTypeAdapterの接続を忘れました。本番環境では、サービスが不適切なJSON値を返し、標準のパーサーが異なるフィールド(ordinalまたはname)をシリアル化し、マイクロサービス間でデシリアル化が一致しませんでした。