什么Scala概念用于使Scalatra DSL工作?

时间:2014-07-11 08:29:36

标签: scala scalatra

我试图通过尝试使用Scalatra来尝试进入Scala。我不久前在课程上完成了Martin Odersky的课程,但我仍然很难理解这是如何工作的:

package com.example.app
import org.scalatra._

class HelloWorldApp extends ScalatraFilter {
  get("/") {
    <h1>Hello, {params("name")}</h1>
  }
}

此示例来自Scalatra主页:http://www.scalatra.org/

如何执行此声明:

get("/") {
    Hello, {params("name")}
}

{}get()方法的参数吗? 你能解释一下Scala语言的哪些特性在用吗? Scalatra源代码的指针将是完美的定义,这将是完美的。

2 个答案:

答案 0 :(得分:8)

getCoreDsl中定义如下

def get(transformers: RouteTransformer*)(block: => Any): Route

因此,get采用两个参数,一系列路由变换器(字符串被隐式转换为路由变换器)和一个无参数方法,输出Any类型的东西。这里有趣的部分是第二个参数。

首先要理解的是,无参数方法作为函数参数是在Scala中专门处理的,即按名称调用,请参阅Automatic Type-Dependent Closure ConstructionScala Language Reference, Section 6.6, p. 78, which is p. 86 of the PDF

  

带有无参数方法类型=> T的形式参数的情况   特别对待。在这种情况下,相应的实际参数   在应用程序之前不评估表达式e。相反,每一个   在重写规则的右侧使用形式参数   需要重新评估e。换句话说,评估顺序   对于=> - 参数是按名称调用而评估顺序是   正常参数是按值调用

第二个方面是在函数应用程序中,参数可以包含在()(&#34;常规&#34;参数)或{}中(更准确地说,在这种情况下,它们必须是block expressions,他们甚至可以开始新的一行),请参阅Scala Language Reference on Function Application, Section 6.6 on p. 77, which is p. 85 of the PDF

另请注意,这两个功能是如何使Scala成为定义DSL(或类似关键字的新功能)的有吸引力的语言的重要组成部分。

以下问题的某些部分可能也很有趣What's the difference between multiple parameters lists and multiple parameters per list in Scala?

答案 1 :(得分:1)

  

{}是get()方法的参数吗?

是。 get将有两个参数列表。一个用于路径"\",另一个用于块执行。块包含在{}中,()中的参数。所以你似乎必须将其称为

class HelloWorldApp extends ScalatraFilter {
  get("/") ({
    <h1>Hello, {params("name")}</h1>
  })
}

但是有一些语法糖允许传递{}中的单个参数而无需添加()。你会在

之类的东西中看到这种情况
myList foreach { do_something() }

它是一个非常有用的功能,用于编写外观,并且像新的控制结构一样使用,但实际上只是函数。