假设我有一个特征Foo
与几种方法。我想创建一个扩展Foo
的新特性,但是“包装”每个方法调用,例如用一些打印语句(实际上这会更复杂一些/我有几个不同的用例)。混合包装斯卡拉特质的每种方法
trait Foo {
def bar(x: Int) = 2 * x
def baz(y: Int) = 3 * y
}
我可以通过重写每个方法手动执行此操作。但这似乎不必要的冗长(和太容易调用错误的超级方法):
object FooWrapped extends FooWrapped
trait FooWrapped extends Foo {
override def bar(x: Int) ={
println("call")
super.bar(x)
}
override def baz(y: Int) ={
println("call")
super.baz(y)
}
}
scala> FooWrapped.bar(3)
call
res3: Int = 6
我希望写一个mixin特质,那我就可以和其他特点重用,并且使用:
trait FooWrapped extends Foo with PrintCall
这样我就不必手动覆盖每个方法(mixin会为我做这个)。
是否有可能在Scala中编写这样一个mixin特性?它会是什么样子?
它应该是可行的使用宏注释(HTTP://docs.scala-lang .org/overviews /宏/注释),我想。这是一个评论,而不是一个答案,因为我目前无法编写宏。 –
您还可以使用可堆叠特征模式将特定行为附加到现有特征,以便您的调用看起来像:val a = New PrintCall的SomeClass和Logger with Whatever。您只需按照希望执行的顺序注入行为(如果打印和记录它并不重要,但是如果您的特征是AddTwo和MultiplyByThree,那么顺序很重要)。我在评论中写道,因为它不是真正你所要求的,但如果你不熟悉这种模式,请检查它,它可以非常酷(但你确实需要明确地覆盖每个方法)。 – slouc
@slouc我希望有一个解决方案,并不意味着我必须手动为每种方法编写'override def bar'。主要是因为这样做意味着我不能一般性地写出这些(不提前知道所有方法和签名)。 –