Scala 为trait实现扩展function n

Scala 为trait实现扩展function n,scala,Scala,我正试图为自己建立一个小型的模拟库来处理非常明显的情况: 模拟函数并记录对它们的调用 模拟trait实现,并能够记录对实现的方法的调用 我通过以下实现实现了第一个目标: class LoggedFunction1[A1, B](body: A1 => B) extends Function1[A1, B] { val calls = mutable.Buffer[A1]() override def apply(v1: A1): B = { calls +

我正试图为自己建立一个小型的模拟库来处理非常明显的情况:

  • 模拟函数并记录对它们的调用
  • 模拟trait实现,并能够记录对实现的方法的调用
  • 我通过以下实现实现了第一个目标:

    class LoggedFunction1[A1, B](body: A1 => B) extends Function1[A1, B] {
        val calls = mutable.Buffer[A1]()
    
        override def apply(v1: A1): B = {
            calls += v1
            body(v1)
        }
    }
    
    object LoggedFunction {
        def apply[A1, B](body: A1 => B) = new LoggedFunction1(body)
    }
    
    到目前为止,一切顺利

    我现在想知道我是否可以以某种方式使用FunctionN扩展来实现trait的方法,例如:

    trait A {
        def m(i: Int)
    }
    
    class B extends A {
        override def m(i: Int) = LoggedFunction((a: Int) => a)
    }
    
    class C extends A {
        val _m = LoggedFunction((a: Int) => a)
        override def m(i: Int) = _m(i)
    }
    
    现在当然不会编译了,因为
    m
    的返回值必须是
    Int
    类型,而不是
    Function1[Int,Int]

    我可以声明一个伴随值来包含我的信息,例如:

    trait A {
        def m(i: Int)
    }
    
    class B extends A {
        override def m(i: Int) = LoggedFunction((a: Int) => a)
    }
    
    class C extends A {
        val _m = LoggedFunction((a: Int) => a)
        override def m(i: Int) = _m(i)
    }
    
    但是我。我真正想做的是:

    class D extends A {
        override val m = LoggedFunction((a: Int) => a)
    }
    
    在我看来,最新的“应该”在某种程度上起作用,因为我正在用
    Function1[Int,Int]
    覆盖
    Function1[Int,Int]
    ,但它抱怨我没有用
    m
    覆盖任何东西

    有没有可能我可以使用我的
    LoggedFunction
    覆盖
    m
    ,这样我就可以写:

    val test = new E
    test.m(1)
    test.m.calls should have size 1
    
    如果不是:为什么不可能用包含函数的值重写该方法

    在我看来,最新的“应该”在某种程度上起作用,因为我正在用
    Function1[Int,Int]
    覆盖
    Function1[Int,Int]

    用这种方法重写一个函数是行不通的,这两种方法是完全不同的。看

    在您的具体用例中,您可以尝试以下方法:

    override def m(i: Int) = LoggedFunction((a: Int) => a).apply(i)
    

    我猜你的意思是:
    apply(I)
    。是的,这是可行的,但是当您返回到一个普通函数时,您无法到达
    调用
    成员进行内省。按照您的建议,将
    日志函数
    存储在公共val中,这是唯一的方法!