6

コトリン バージョン 1.2.50

YouTube https://www.youtube.com/watch?v=gPH9XnvpoXEのこのチュートリアルのいくつかの例に従っています。そして、私が理解したことがいくつかありますが、まだいくつかの混乱があります. 以下のコードにコメントを残しましたが、何が起こっているのかわかりません。

fun main(args: Array<String>) {

    val javaClient = createClient {
        firstName = "joe"
        lastName = "bloggs"

        twitter {
            handle = "@joebloggs"
        }
    }

    println(javaClient.toConsole)
}

/* Are we passing in a lambda and receiver. What will the receiver be */
private fun JavaClientBuilder.twitter(suppler: JavaTwitterBuilder.() -> Unit) {
    /* We call JavaTwitterBuilder().apply(..) Will apply return the newly created object? Not sure why we have to pass the suppler in the apply */
    twitter = JavaTwitterBuilder().apply(suppler).build()
}

/* Are we passing in a lambda and receiver that return nothing */
private fun createClient(suppler: JavaClientBuilder.() -> Unit): JavaClient {
    val javaClientBuilder = JavaClientBuilder()

    /* confusion: Not sure about this, as we are calling suppler. Just wondering is the suppler the the JavaClientBuilder that was called in the above javaClient {} lambda */
    javaClientBuilder.suppler()

    return javaClientBuilder.build()
}

/* I understand this, an extension function that formats and returns the string from the JavaClient object it was called on */
private val JavaClient.toConsole: String
    get() =
        "Created client is: ${twitter.handle} ${company.name}"
4

2 に答える 2

9

/* ラムダとレシーバーを渡していますか。レシーバーはどうなりますか */

プライベートで楽しい JavaClientBuilder.twitter(提供元: JavaTwitterBuilder.() -> Unit)

この関数には確かにレシーバーがあり、それはJavaClientBuilderこの関数が呼び出されるインスタンスです。

/* JavaTwitterBuilder().apply(..) を呼び出します。apply は新しく作成されたオブジェクトを返しますか? 申請でサプライヤーを渡さなければならない理由がわかりません */

twitter = JavaTwitterBuilder().apply(サプライヤー).build()

どのように機能するかを理解するapply()には、そのソース コード (簡易版) を見てください。

public inline fun <T> T.apply(block: T.() -> Unit): T {
    block()
    return this
}

これは、タイプのレシーバーで宣言され、ブロックを受け取るTのインスタンスを返す拡張関数です。これは通常、Builder パターンを置き換えるために使用されます - カスタム初期化ロジックをオブジェクトに適用します。あなたの場合、のインスタンスの初期化ロジックを含むブロックです。関数コードはインスタンスを作成し、ロジックで使用してそのインスタンスを初期化します。TTUnitsupplerJavaTwitterBuilderapply()suppler

/* 何も返さないラムダとレシーバーを渡していますか */

private fun createClient(suppler: JavaClientBuilder.() -> Unit): JavaClient

この場合、 にcreateClient()はレシーバーがなく、トップレベルの関数です。

/* 混乱: suppler と呼んでいるので、これについてはわかりません。上記の javaClient {} ラムダ */

javaClientBuilder.suppler()

supplerはレシーバー型であるラムダですJavaClientBuilder。これにより、新しく作成された のインスタンスで呼び出すことができますJavaClientBuilder

/* これは、呼び出された JavaClient オブジェクトから文字列をフォーマットして返す拡張関数です */

private val JavaClient.toConsole: String get() = "作成されたクライアントは: ${twitter.handle} ${company.name}"

右!ちょっとした訂正ですが、これは拡張プロパティです。プロパティには、カスタムのゲッターとセッターを含めることができます。このプロパティはカスタム ゲッターを定義するため、実際にこのプロパティにアクセスすると、ゲッター コードで記述された形式の文字列が生成されます。

于 2018-10-07T14:43:38.737 に答える