2016-09-28 3 views
0

Когда вы видите код, который следует схеме:Анонимные функции с параметрами

def index = Action { request => 
    // .. 
} 

Действие черта: https://github.com/playframework/playframework/blob/master/framework/src/play/src/main/scala/play/api/mvc/Action.scala#L65

При взгляде на этот код, как вы знаете, что объект запроса доступен для использования в блок кода? (есть ли для этого ярлык intellij?)

Может кто-нибудь, пожалуйста, создайте миниатюрный пример того, где вы можете подражать этому шаблону, чтобы я мог понять, как это работает, и если вы можете технически объяснить, что происходит?

ответ

1

Это называется Loan pattern

withWriter создает писатель для пользователя, а затем обеспечивает ресурс (писатель) должным образом тесно после использования.

Все, что пользователь должен сделать, это просто использовать writer и написать что-то в файл

def withWriter(file: File)(f: Writer => Unit): Unit = { 
    val writer = new PrintWriter(file) 
    try { 
    f(writer) 
    } finally { 
    writer close 
    } 
} 

Использование:

withWriter(new File("some_fix.txt") { writer => 
    writer println("write something") 
} 
+0

Вы уверены, что это шаблон кредита, так как это определенно имеет отношение к управлению ресурсами? Я не читал источник воспроизведения, но [эта страница] (https://www.playframework.com/documentation/2.5.x/ScalaActions) только упоминает, что он принимает функцию –

3

Actionчерта не представляет интереса здесь. Вместо этого, потому что тело метода index должно быть значение, не типа, вы смотрите на Actionобъекта. Вы можете узнать больше об объектах here. Давайте сначала упростим синтаксис, удалив синтаксический сахар, т. Е. Сделав программу одинаковой, но с более простыми конструкциями. Если вы пытаетесь вызвать объект, как если бы это был метод, что на самом деле происходит то, что .apply вставляется для вас компилятором:

def index = Action.apply((request) => { 
    // .. 
}) 

Это может быть более знакомы; метод apply вызывается на объекте Action, передавая функцию лямбда, которая принимает запрос. И, очевидно, аргумент в лямбда всегда доступен в этой лямбде. В этом их суть.

Лямбда в этом случае также называется обратным вызовом . Простой пример, поясняющий эти функции:

object WithAnswer { 
    def apply(f: Int => Unit): Unit = 
    f(42) 
} 

def printAnswer() = WithAnswer { answer => 
    println(answer) 
} 
+0

Спасибо. Да, вы передаете запрос на лямбду, и поэтому вы можете использовать его внутри ламбы, я так понимаю. Но откуда вы знаете, какие параметры доступны? Может ли IntelliJ сказать мне это легко или? –

+0

в вашем примере у вас есть параметр «ответ», что это? –

+0

Это целое число, которое 'WithAnswer.apply' переходит на лямбду. – rightfold

Смежные вопросы