问题描述
我有以下操作
def login: Result = Action(parse.json) { request =>if (/* 让我们说这是一些验证 */) {返回 BadRequest("坏")}好的(一切都好")}
这给了我一个错误.Intellij 建议 Action[JsValue]
类型.当我说返回将是那种类型时,我在 BadRequest
行上再次出错,因为类型不匹配.
我尝试搜索这个问题,我发现了一些建议将 Action[AnyContent]
设置为返回类型的答案.但我仍然收到错误.
我还需要从 if
返回...我不想在 if
之后写 else
,因为在一些复杂的函数很可能我会有很少的 if
语句来中断操作,如果我使用 if/else
方法,代码将是一场噩梦.
当然可以.在 Scala 中,嵌套匿名函数中的return"语句是通过抛出和捕获 NonLocalReturnException 来实现的.在 Scala 语言规范,第 6.20 节中是这样说的.>
这样做是为了理解,让人们能够编写这样的代码:
def loop() = {for (i <- 0 到 20) {if (someCondition) 返回}}
那个循环实际上相当于:
(0 到 20).foreach { i =>if (someCondition) 返回 }
你能看到匿名函数吗?你能看到有问题的返回"不是指单独从那个匿名函数返回吗?在我看来,这是一个设计错误.另一方面,在像 Scala 这样的语言中,无论如何都不需要返回".
所以你有一个匿名函数:
Action(parse.json) { request =>......这里的这个...... }
在该函数中,您使用了return",它在幕后触发了异常.
所以 Scala 中的一般经验法则 - 永远,永远不要使用返回.无论如何,它是一种面向表达式的语言.你不需要它.
Action(parse.json) { request =>if (/* 让我们说这里是一些验证 */)错误请求(坏")别的好的(一切都好")}
那里,更加地道.顺便说一句 - 你也没有休息"或继续".习惯没有他们的工作.另外,关于您的意见:
<块引用>此外,我需要从 if 返回...我不想在 if 之后写 else,因为在一些更复杂的函数中,我很可能只有很少的 if 语句应该中断操作,如果我使用 if/否则,代码将是一场噩梦.
这是错误的,我真的很讨厌使用依赖返回、中断或继续来使逻辑短路的代码,因为复杂的逻辑变得混乱,我想清楚地看到:
不变量,如果我们谈论的是循环退出条件分支/路径使用 return、break 或 continue 会破坏所有 3 点的清晰度.它们并不比 GOTO 跳跃好多少.如果你有复杂的功能,如果阅读开始成为一个问题,就把它们分解成多个功能.
此外,比多个if/else"分支更好的是match"语句.一旦习惯了它们,您就会爱上它们,尤其是考虑到编译器甚至可以在您缺少分支的某些情况下保护您.
I have following action
def login: Result = Action(parse.json) { request =>
if (/* Let's we say here is some validation */) {
return BadRequest("bad")
}
Ok("all ok")
}
This is giving me an Error. Intellij is suggesting Action[JsValue]
type. When I say return will be of that type, I am getting again error on BadRequest
line, because types doesn't match.
I tried searching about this problem, and I found some answers which are suggesting to set Action[AnyContent]
as return type. But I am STILL getting error.
Also I need to return from if
...I don't want to write else
after that if
, because in some more complex function most probably I will have few if
statements which should break action, and if I use if/else
approach, code will be nightmare.
Of course it does. In Scala, a "return" statement inside a nested anonymous function is implemented by throwing and catching a NonLocalReturnException. It says so in the Scala Language Specification, section 6.20.
This is done because of for comprehensions, for people to be able to write code like this:
def loop() = {
for (i <- 0 until 20) {
if (someCondition) return
}
}
That loop is actually equivalent to:
(0 until 20).foreach { i => if (someCondition) return }
Can you see the anonymous function? Can you see that the "return" in question doesn't refer to returning from that anonymous function alone? In my opinion this was a design mistake. On the other hand, in a language like Scala, "return" isn't needed anyway.
So you have an anonymous function in there:
Action(parse.json) { request => ... this one here ... }
And inside that function you're using "return" which under the hood triggers an exception.
So the general rule of thumb in Scala - NEVER, EVER USE RETURN. It's an expression-oriented language anyway. You don't need it.
Action(parse.json) { request =>
if (/* Let's we say here is some validation */)
BadRequest("bad")
else
Ok("all ok")
}
There, much more idiomatic. BTW - you also don't have "break" or "continue". Get used to working without them. Also, about your opinion:
Also I NEED to return from if...I don't want to write else after that if, because in some more complex function most probably I will have few if statements which should break action, and if I use if/else approach, code will be nightmare.
That is wrong and I REALLY HATE working with code that relies on return, break or continue for short-circuiting the logic PRECISELY because complex logic gets messy and I want to have a clear view of:
invariants, if we are talking about a loop exit conditions the branches / pathsUsing return, break or continue destroys clarity on all 3 points. They aren't much better than GOTO jumps. And if you have complex functions, break them into multiple functions if reading it starts to become a problem.
Also, much better than multiple "if/else" branches are "match" statements. Once you get used to them, you'll love them, especially given that the compiler can even protect you in some cases in which you're missing a branch.
这篇关于从游戏动作中显式返回的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!
更多推荐
[db:关键词]
发布评论