模式匹配:使用 Partial 函数拆分代码



我正在努力实现一种"简单"的行为:将模式匹配代码划分为两个单独的函数。

为了清晰起见,我正在简化模型:

abstract class Animal
case object Dog extends Animal
case object Cat extends Animal
case object Bird extends Animal
case object Bat extends Animal
case object Dolphin extends Animal

我想在不同的函数上对这些进行模式匹配(因为实际代码很长(,但还有其他参数,所以 Partial Functions 让我生病了......
在一个完美的世界里,我可以写:

type PF = PartialFunction[(Animal, Int, String), String] 
private def processFlying(a: Animal, n: Int, loc: String): PF = {
  a match {
    case Bird => n + " birds found in " + loc
    case Bat => n + " bats found in " + underground(loc)
  }
}
private def processMarine(a: Animal, n: Int, loc: String): PF = {
  a match {
    case Dolphin => n + " dolphins found in " + submarine(loc)
  }
}
private def processPet(a: Animal, n: Int, loc: String): PF = {
  a match {
    case Dog => n + " dogs found in " + loc
    case Cat => n + " cats found in " + loc
  }
}
def processAnimal(a: Animal, number: Int, location: String) = {
  val processAll = processFlying orElse processMarine orElse processPet
  processAll(a, n, location)
}

但是,这不起作用。主要是因为我的函数中需要几个参数。"为什么你没有使用元组?"你会说吗?好吧,我试过了,编译器不会停止抱怨预期类型与实际类型不同,并且与我的别名不同:(

任何帮助、提示或替代 ide 都将很有用!
干杯


编辑:我按照西里尔的回答,但我还需要在比赛前做一些工作,比如这样:

val processFlying: PF = {
  // doSomething, like declare a sub-function f
  {
      case (b: Bird, n, loc) => f(b)
      case (b: Bat, n, loc) => f(b)
  }
}

您的问题是您混合了方法定义和函数定义。

def processFlying(a: Animal, n: Int, loc: String): PF

是一个方法(你周围对象的(的签名,它接受三个参数并返回一个PF,即一个PartialFunction[(Animal, Int, String), String]

因此,假设此签名是您想要的,则只有在您已经拥有AnimalIntString的情况下,您才能获得PartialFunction......

您更可能想要的是定义一个PF值(没有参数(,因此更像

val processFlying: PF = {
  case (Bird, n, loc) => ...
  case (Bat, n, loc) => ...
}

编辑

为了回答你的第二个请求(尽管这可能是矫枉过正,因为将你的助手定义为私有 def 就可以完成了这项工作(,你总是可以将 PF 块放在闭包中:

val processFlying = {
  def f = ...
  val res = {
    case (Bird, n, loc) => f(...)
    case (Bat, n, loc) => f(...)
  }
  res
}

但是,您必须为PartialFunction定义块分配一个值,否则解析器将不知道如何处理它。这只是因为PartialFunction具有case块和闭包的定义共享{}语法。

相关内容

  • 没有找到相关文章