【问题标题】:Operator precedence for sum and division on list in ScalaScala中列表上的求和和除法的运算符优先级
【发布时间】:2017-05-11 11:33:30
【问题描述】:

我的示例使用 sum 函数,但这不是我遇到问题的唯一高阶函数。

重点

已经有一段时间了,但我一直在写这样的代码:

scala> List(2, 5, 7, 11) sum / 3

这给了我:

<console>:1: error: ';' expected but integer literal found.

当我添加括号时:

(List(2, 5, 7, 11) sum) / 3

我得到了我的期望:

res3: Int = 8
  1. 所以这是我的问题。为什么运算符优先级会这样工作?为什么它不推断括号?

  2. 是否有任何反例可以表明这种推断会导致 scala 中出现根本错误的结果?

  3. 为什么使用.会改变任何东西。为什么l.sum / 13 有效?

【问题讨论】:

  • 一方面,后缀运算符(如List(2, 5, 7, 11) sum 中的sum)已经隐藏在标志后面一段时间了。我认为它们或多或少已被弃用。

标签: scala list sum higher-order-functions operator-precedence


【解决方案1】:

Scala 中的运算符优先级由一组规则定义。你可以在这里找到它:http://docs.scala-lang.org/tutorials/tour/operators.html

如您所见,字母数字字母(例如sum)的优先级最低。但是,这仅适用于您以中缀形式(不带点)编写函数的情况。

这样写表达式可以解决你的问题:

List(2, 5, 7, 11).sum / 3

就个人而言,我从不调用没有点的后缀函数。 Scala 编译器甚至会在您编写没有 / 3 部分的情况下给您一个警告:

scala> List(1,2,3,4) sum
<console>:12: warning: postfix operator sum should be enabled
by making the implicit value scala.language.postfixOps visible.
This can be achieved by adding the import clause 'import scala.language.postfixOps'
or by setting the compiler option -language:postfixOps.
See the Scaladoc for value scala.language.postfixOps for a discussion
why the feature should be explicitly enabled.
   List(1,2,3,4) sum

【讨论】:

    【解决方案2】:

    回答你的第三个问题:

    为什么使用. 会改变任何东西。为什么l.sum / 13 有效?

    让我们来一段更通用的代码:

    a b c d
    

    Scala 应该如何解释这个? a.b.c.d? a.b(c).d? a.b.c(d)?事实是 Scala 总是 将其解释为 a.b(c).d,即使它没有正确进行类型检查。为什么这样做?因为如果 Scala 决定根据程序的上下文对a b c d 进行不同的解释,那么程序的读者将很难非常理解他们正在阅读的代码的含义。

    所以如果a.b.c(d) 是你想要的,你必须写a.b c d 这样代码才能被明确地解释。

    【讨论】:

      猜你喜欢
      • 2011-06-21
      • 2020-03-05
      • 1970-01-01
      • 2011-09-16
      • 2014-11-09
      • 2021-03-16
      • 2020-08-04
      • 1970-01-01
      • 2021-03-29
      相关资源
      最近更新 更多