2017-08-25 4 views
13

Ich habe die Dokumente dreimal gelesen und ich habe immer noch keine Ahnung, was es tut. Kann jemand ELI5 (Erkläre, wie ich fünf bin) es bitte? Hier ist, wie ich verwende es:Was bedeutet "mit" in Kotlin?

fun main(args: Array<String>) { 
    val UserModel = UserModel() 
    val app = Javalin.create().port(7000).start() 

    with (app) { 
     get("/users") { 
      context -> context.json(UserModel) 
     } 
    } 
} 
+3

Wow, Ihre Frage hat mir klar gemacht, dass es keine gute Dokumentation darüber gibt, was "mit" macht - eine ** Funktion ** zu sein, kein Schlüsselwort - tatsächlich funktioniert! Also schrieb ich eine Frage und beantwortete sie auf die gleiche Art, vielleicht fügt sie den bereits vorhandenen Antworten einen gewissen Wert hinzu. Siehe: [Was ist ein "Empfänger" in Kotlin?] (Https://stackoverflow.com/q/45875491/7079453) –

+1

Warten Sie immer noch auf eine Antwort? ;-) – s1m0nw1

Antwort

9

Die documentation sagt:

inline fun <T, R> with(receiver: T, block: T.() -> R): R (source)

Ruft den angegebenen Funktionsblock mit dem angegebenen Empfänger als Empfänger und gibt sein Ergebnis.

So wie ich daran denke, dass es eine Funktion (die block), wo this im Rahmen der block ist die receiver ruft. Was immer block zurückgibt, ist der Rückgabetyp.

Im Wesentlichen Aufruf einer Methode, wo Sie die implizite this bereitstellen und jedes Ergebnis daraus zurückgeben können. Hier

ist ein Beispiel zu demonstrieren:

val rec = "hello" 
val returnedValue: Int = with(rec) { 
    println("$this is ${length}") 
    lastIndexOf("l") 
} 

Die rec in diesem Fall ist der Empfänger der Funktionsaufruf - die this im Rahmen des block. Die $length und lastIndexOf sind beide am Empfänger angerufen.

Der Rückgabewert kann ein Int sein, da das der letzte Methodenaufruf in body ist - das ist der generische Typ Parameter R der Signatur.

+0

Also ist es nur ein Werkzeug um zu sagen, in welchem ​​Bereich du sein möchtest? –

+1

@VladyVeselinov im Wesentlichen, ja. Es gibt ein paar andere Scoping-Funktionen, die Ihnen helfen können, den Code klarer zu machen. Im [yole/kotlin-style guide GitHub-Repository] (https://github.com/yole/kotlin-style-guide/issues/35) finden Sie einige Beispiele und Diskussionen über allgemeine Nutzungsmuster. – mkobit

2

with wird verwendet, um auf die Elemente und Methoden eines Objekts zuzugreifen, ohne einmal pro Zugriff auf das Objekt verweisen zu müssen. Es ist (meistens) für die Abkürzung Ihres Codes. Es wird häufig verwendet, wenn ein Objekt konstruieren:

// Verbose way, 219 characters: 
var thing = Thingummy() 
thing.component1 = something() 
thing.component2 = somethingElse() 
thing.component3 = constantValue 
thing.component4 = foo() 
thing.component5 = bar() 
parent.children.add(thing) 
thing.refcount = 1 

// Terse way, 205 characters: 
var thing = with(Thingummy()) { 
    component1 = something() 
    component2 = somethingElse() 
    component3 = constantValue 
    component4 = foo() 
    component5 = bar() 
    parent.children.add(this) 
    refcount = 1 
} 
+0

Dies ist auch eine gute Zeit, um darauf hinzuweisen, dass dies die Unveränderlichkeit fördert; das zweite 'var-Ding' sollte zu einem' val-Ding' werden und garantieren, dass es sich nie ändert, es sei denn, du möchtest, dass es sich ändert – Supuhstar

5

Die Definition von with:

inline fun <T, R> with(receiver: T, block: T.() -> R): R (source) 

Eigentlich ist es die Umsetzung gerade nach vorne: Die block auf receiver ausgeführt wird, die für jede Art arbeitet:

receiver.block() //that's the body of `with` 

Das großartige, hier zu erwähnen, ist der Parametertyp T.() -> R: Es heißt function literal with receiver. Es ist ein Lambda, der auf die Mitglieder des Empfängers ohne zusätzliche Qualifier zugreifen kann.

In Ihrem Beispiel wird auf diese Weise auf den context von with Empfänger app zugegriffen.

Neben stdlib Funktionen wie with oder apply ist diese Funktionalität, was zum Schreiben Kotlin groß macht Domain Specific Languages ​​ wie es die Schaffung von Bereichen ermöglicht, in dem Sie den Zugriff auf bestimmte Funktionalitäten aufweisen.