如何使用不可变集合和if语句编写适当的Scala?

时间:2012-11-14 21:47:16

标签: scala collections scala-collections

我想要以下功能:采取以下参数:

  • def filters: Map[String, String]
  • def queryString: Map[String, Seq[String]](来自request.queryString)
  • def key: String

..如果queryString包含参数中指定的key,我想将相应的值添加到filters

工作职能是:

private def getUpdatedFiltersIfQueryStringContains(filters: Map[String, String], queryString: Map[String, Seq[String]], key: String): Map[String, String] = {
  var updatedFilters: Map[String, String] = filters

  if (queryString.contains(key)) {
    updatedFilters = updatedFilters ++ Map(key -> queryString.get(key).get.head)
  }

  updatedFilters
}

这看起来很可怕,对吧?

由于if语句在Scala中返回内容,我期待更多内容:

private def getUpdatedFiltersIfQueryStringContains(filters: Map[String, String], queryString: Map[String, Seq[String]], key: String): Map[String, String] = {
  if (queryString.contains(key)) {
    filters ++ Map(key -> queryString.get(key).get.head)
  }
}

但这不编译,错误是:

  

类型不匹配; found:需要的单位:Map [String,String]

3 个答案:

答案 0 :(得分:5)

您可以使用更多monadic

queryString.get(key) map { v => filters ++ Map(key -> v.head) } getOrElse filters

做你想做的事。

答案 1 :(得分:5)

这是一个更加惯用的实现,不使用if

def getUpdatedFiltersIfQueryStringContains(filters: Map[String, String], queryString: Map[String, Seq[String]], key: String): Map[String, String] =
  filters ++ queryString.get(key).map(key -> _.head)

答案 2 :(得分:4)

你的函数签名声明应该返回Map[String, String],但是......等一下,想象一下,如果queryString不包含密钥怎么办?好吧,看起来什么都不会被退回,而且Scala中没有任何东西(至少有一种类型)。

要解决这个问题,您需要提供替代方案:

private def getUpdatedFiltersIfQueryStringContains(filters: Map[String, String], queryString: Map[String, Seq[String]], key: String): Map[String, String] = {
    if (queryString.contains(key)) {
      filters ++ Map(key -> queryString.get(key).get.head)
    } else filters
  }

顺便说一句,函数名真的让我害怕