从案例类获取最大值节点列表,返回Scala选项[列表]

时间:2017-08-27 02:19:45

标签: scala

我有一个我编写的案例类Node,并从中创建一个列表,我需要找到具有最大磁盘的节点。 我写了下面的代码,有没有更好的方法呢?另外,在我的实际生产代码中,我的" nodeList"变量不只是Option[List[Node]]而是Future[Option[List[Node]]]。我想答案/代码仍然不会发生太大的变化,除了我会做一个map / flatMap以便进入未来并做同样的事情。 如果有人有更好的建议在下面写代码更多Scala方式,请分享您的想法。

scala> case class Node(disk: Integer, name: String)

定义的类Node

scala> val nodeList = Option(List(Node(40, "node1"), Node(200, "node3"),Node(60, "node2")))
nodeList: Option[List[Node]] = Some(List(Node(40,node1), Node(200,node3), Node(60,node2)))

scala> val maxDisk = nodeList match {
| case None => println("List is empty"); None
| case Some(lst) => {
| Some(lst.max(Ordering.by((_:Node).disk)))
| }
| }`
maxDisk: Option[Node] = Some(Node(200,node3))

2 个答案:

答案 0 :(得分:1)

根据您编写的代码判断,我不确定您是否真的应该使用Optional[List[Node]]。您似乎将None视为空List,并且您不会检查Some案例中的空列表。您可能希望看一下普通的List[Node]是否更适合您的使用(None将成为Nil,而Some(lst)只是lst,并且未使用Some(Nil)不再存在让任何人混淆的情况。

如果你保留Optional[List[Node]],我会这样做:

nodeList
  .filterNot(_.isEmpty) // maxBy throws if the list is empty; check for it
  .map(_.maxBy(_.disk)) // maxBy looks nicer than max(Ordering.by)

如果你切换到List[Node],那就更加丑陋了:

Some(nodeList)
  .filterNot(_.isEmpty) // We're using the filter utility of Option here,
  .map(_.maxBy(_.disk)) // so I wrap with Some to get access to filterNot.

答案 1 :(得分:1)

您可以将递归与列表模式匹配一​​起使用。

  case class Node(disk: Integer, name: String)
  val nodeList = Option(List(Node(40, "node1"), Node(200, "node3"),Node(60, "node2")))

  def findMaxValue(list: List[Node]): Option[Node] = list match {
    case Nil => None
    case List(x) => Some(x)
    case first :: second :: rest => if(first.disk > second.disk) findMaxValue(first::rest) else findMaxValue(second::rest)
  }

  val node:Option[Node] = findMaxValue(nodeList.getOrElse(Nil))
  println(node.get.disk)  //print 200