【问题标题】:A better way to test the value of an Option?测试期权价值的更好方法?
【发布时间】:2010-12-09 08:55:55
【问题描述】:

我经常发现自己对某些类型的T 有一个Option[T],并希望根据某个值测试该选项的值。例如:

val opt = Some("oxbow")
if (opt.isDefined && opt.get == "lakes") 
   //do something

下面的代码是等价的,去掉了测试选项值的存在性的要求

if (opt.map(_ == "lakes").getOrElse(false))
 //do something

但是,这对我来说似乎不太可读。其他可能性是:

if (opt.filter(_ == "lakes").isDefined)

if (opt.find(_ == "lakes").isDefined) //uses implicit conversion to Iterable

但我认为这些也不能清楚地表达意图,这会更好:

if (opt.isDefinedAnd(_ == "lakes"))

有没有人有更好的方法来做这个测试?

【问题讨论】:

    标签: scala option code-readability


    【解决方案1】:

    怎么样

    if (opt == Some("lakes"))
    

    这清楚地表达了意图并且直截了当。

    【讨论】:

    • 有时最简单的解决方案是最好的:)
    • 即使opt 不是选项,这是否仍然可以编译?
    【解决方案2】:

    对于 Scala 2.11,您可以使用 Some(foo).contains(bar)

    【讨论】:

    • 这就是我通常的方式。我只是无法理解这个答案不被接受为正确的答案。
    【解决方案3】:

    Walter Chang FTW,但这是另一个尴尬的选择:

    Some(2) exists (_ == 2)
    

    【讨论】:

    • 丹尼尔,那是可怕:-)
    • 我其实很喜欢这个;避免一次创建和一次未应用,但简洁
    • 就我而言,这实际上是标准方式。
    • 有点遗憾,Option 没有隐式转换为Seq,这将允许Some(1) contains 1
    • 也许 contains 应该直接添加到 Option 中。
    【解决方案4】:
    val opt = Some("oxbow")
    opt match {
      case Some("lakes") => //Doing something
      case _ => //If it doesn't match
    }
    

    【讨论】:

      【解决方案5】:

      你也可以使用理解:

      for {val v <- opt if v == "lakes"}
        // do smth with v
      

      【讨论】:

        【解决方案6】:

        我认为也可以使用模式匹配。这样您就可以直接提取有趣的值:

        val opt = Some("oxbow")
        opt match {
          case Some(value) => println(value) //Doing something
        }
        

        【讨论】:

        • 这不会针对该值进行测试 - 只是它存在。我想避免使用match 的原因是,这会导致else 逻辑位于多个位置(即case None,如果该值不是所需的值)
        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2016-04-18
        • 1970-01-01
        • 2014-08-31
        • 2012-11-11
        相关资源
        最近更新 更多