【问题标题】:Higher Order Function with Case Class Method具有案例类方法的高阶函数
【发布时间】:2020-11-19 07:14:51
【问题描述】:

我正在尝试删除代码中的冗余。我想我可以用高阶函数来做到这一点。

我要做的是将公共位分解到f3中,然后将f1和f2之间不同的位作为传递给f3的参数。

object Example extends App {

  case class action(name: String, age: Int) {
    def setName(new_name: String): action = this.copy(name = new_name)
    def setAge(new_age: Int): action = this.copy(age = new_age)
  }

  def f1(x: action, increment: Int) = {
    // big block of code which does a....

    // a single line in the block calling
    val older_person = x setAge (x.age + increment)

    // big block of code which does b....
  }

  def f2(x: action, new_name: String) = {
    // big block of code which does a....

    // a single line in the block calling
    val new_name_person = x setName new_name

    // big block of code which does b....
  }

  /* Now as there is clearly a redundancy, which can be solved by higher order functions.
    I want to combine f1 and f2 into a single function. The function will take in the action, the value, and the 
    function to apply. It will then call the relevant function inside the method.
   */
  def f3[T](x: action)(f: T => action)(value: T) = {
   // big block of code which does a....
   // call x.f(value)
    val new_action = ??? 
   // big block of code which does b....
  }

  // then in my code I can call like this:
  // f3(x)(setAge)(100)
  // f3(x)(setName("new_name")
}

我很困惑的是如何传入一个作为案例类中的方法的函数?有没有一种优雅的方式来做到这一点?

【问题讨论】:

    标签: scala higher-order-functions abstraction case-class


    【解决方案1】:

    在f3 中,您可以简单地接受Action => Action 类型的函数(我将使用Action 而不是action 以减少混淆)。

    def f3(x: Action)(copy: Action => Action) = {
      // big block of code which does a....
    
      // a single line in the block calling
      val new_name_person = copy(x)
    
      // big block of code which does b....
    }
    

    然后你可以定义一些有用的函数,并使用currying让它们以后更容易使用:

    object Action {
      def setName(name: String)(action: Action) = action.copy(name=name)
      def incAge(inc: Int)(action: Action) = action.copy(age=action.age+inc)
    }
    

    然后像这样使用它:

    val x = Action("Foo", 42)
    f3(x)(Action.incAge(100))
    f3(x)(Action.setName("new_name"))
    

    Try it in Scastie

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-05-29
      • 2013-04-23
      • 2020-03-11
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多