2

我想定义一个可以比较两种类类型的函数。我定义了两个不同的类:

abstract class Task
case class DefinedTask(id: Long) extends Task
case class EmptyTask() extends Task  

然后我有一个返回类型对象的函数Task,它可以是DefinedTaskEmptyTask

现在,我想做的是有一个函数来识别这个对象是 aDefinedTask还是只是一个EmptyTask. 问题很简单,我会使用模式匹配。但我想概括它,因为多个类都采用这种Defined/Empty模式。

到目前为止我尝试的是:

def makeReturned[T: Manifest, U: Manifest](obj: T)(u: U)(f: T => Value) = 
   if(manifest[U] equals manifest[T]) f(obj) else
     throw new IllegalArgumentException()
}
//call to it
makeReturned(task)(DefinedTask)(makeTask)

U总是DefinedTaskT可能是DefinedTask or EmptyTask,但它返回为Task.

manifest[U].erasure.toString //"class DefinedTask$"
manifest[T].erasure.toString //"class Task"  

从编译器的角度来看这是正确的,但它不适合我。所以,我的问题是我怎样才能以一种能给我想要的方式比较它们?

4

2 回答 2

1

看起来您想要运行时检查,而不是编译时检查。所以我认为你的意思是

def makeReturned[U <: Task, T <: Task](obj: T)(u: U)(f: T => Value) = {
  if (obj.getClass.isInstance(u.getClass)) f(obj)
  else throw new IllegalArgumentException
}

或类似的东西。查看方法,java.lang.Class然后选择可以满足您需求的方法。

于 2012-11-07T18:29:07.893 回答
1
  1. 您的代码中有一些错误:
    • 您应该abstract class Task为详尽的模式匹配进行密封
    • 不推荐使用空案例类。编译器应该已经警告过你了。case object EmptyTask extends Task将是正确的选择
  2. 案例类和案例对象都扩展了 trait Product。您可以通过以下任一方式检查产品是否为空:
    • task.productArity == 0
    • task.productIterator.isEmpty
  3. 我认为你最好重新处理你的问题。为什么不直接使用标准Option并在其中包含简单的实例case class Task(id: Int)?这可能是您所有其他类似实体的一般方法。
于 2012-11-07T21:02:01.183 回答