class ModelFactory {
fun setA() : ModelFactory {
// blabla...
}
fun setB() : ModelFactory {
// blabla...
}
fun setC() : ModelFactory {
// blabla...
}
fun build() : Model {
// An error occurs if any of setA, setB, and setC is not called.
}
}
//example
fun successTest() {
ModelFactory().setA().setB().setC().build() // No error occurs at compile time
}
fun failTest() {
ModelFactory().setA().build() // An error occurs at compile time because setB and setC are not called.
}
文法的にはぎこちないですが、自分の思い通りに表現されていると思います。
この要件に対してエラー発生ランタイムをすでに実装しましたが、コンパイル時にこれを確認したいと思います。
可能であれば、注釈を使用する必要があると思います。しかし、これはコンパイル時に本当に可能ですか?
Kotlinでは、必須ではないフィールドに常にデフォルト値を指定できるため、ビルダーパターンを避けてきました。
それでもビルダーパターンを使用したい場合は、オブジェクトを作成する前にすべての必須フィールドが設定されることを期待するステップビルダーパターンを使用できます。各セッターメソッドは、次のセッターインターフェイスの参照を返すことに注意してください。必須フィールドの組み合わせに基づいて、複数のステップビルダーを作成できます。
class Model(val a: String = "", val b: String = "", val c: String = "")
class StepBuilder {
companion object {
fun builder(): AStep = Steps()
}
interface AStep {
fun setA(a: String): BStep
}
interface BStep {
fun setB(b: String): CStep
}
interface CStep {
fun setC(c: String): BuildStep
}
interface BuildStep {
//fun setOptionalField(x: String): BuildStep
fun build(): Model
}
class Steps : AStep, BStep, CStep, BuildStep {
private lateinit var a: String
private lateinit var b: String
private lateinit var c: String
override fun setA(a: String): BStep {
this.a = a
return this
}
override fun setB(b: String): CStep {
this.b = b
return this
}
override fun setC(c: String): BuildStep {
this.c = c
return this
}
override fun build() = Model(a, b , c)
}
}
fun main() {
// cannot build until you call all three setters
val model = StepBuilder.builder().setA("A").setB("B").setC("C").build()
}
この記事はインターネットから収集されたものであり、転載の際にはソースを示してください。
侵害の場合は、連絡してください[email protected]
コメントを追加