当前位置:  开发笔记 > 编程语言 > 正文

Scala中的管道运营商

如何解决《Scala中的管道运营商》经验,为你挑选了1个好方法。

我想知道是否可以像%>%在语言magrittr包中那样定义管道运算符R。我发现了几个类似的实现,如下所示:

implicit class PipelineContainer[F](val value: F) {
  def |>[G] (f: F => G) = f(value)
}

所以x |> f |> gg(f(x))

现在,我希望即使在函数使用多个参数的情况下,该运算符也可以工作,在这种情况下,管道参数左侧的值将成为右侧函数的第一个参数。例如,x |> f(2) |> g(3)变为g(f(x, 2), 3)。如何在Scala中实现此功能?它的语法不必与我在此处显示的相同,但是越简单越好。



1> Rex Kerr..:

有一些选择。

一种是只创建内联函数。只是有点混乱。

x |> (z=>f(z,2)) |> (z=>g(z,3))

另一种方法是创建可以使现有功能崩溃的快捷方式。总的来说,这是很多样板,但是第一个很简单:

implicit class RichPipes[Y](y: Y) {
  def |>[Z](f: Y => Z) = f(y)
  def &>[X, Z](f: (X, Y) => Z): (X => Z) = (x: X) => f(x, y)
}

然后,您可以内联注入其他参数(利用&优先级高于的事实|):

x |> 2 &> f |> 3 &> g

我个人觉得这种样式令人困惑,但是编译器对此很好。

另一个选择是将这些方法转换为以(例如必要)开头的函数,然后丰富这些函数以使用部分应用程序帮助程序方法:

implicit class RichFunction2[A,B,Z](f: (A,B) => Z) {
  def %(b: B): (A => Z) = (a: A) => f(a,b)
}

现在你可以

x |> f _ % 2 |> g _ % 3

最后,如果您碰巧能够以不同的方式编写函数,则可以使其运行而无需任何额外的机制,而不必添加任何痕迹_,让编译器知道您的工作。区别仅在于应用程序经过多个参数块的最后一个:

def h(y: Int)(x: Int) = x + y
def i(y: Int)(x: Int) = x * y

x |> h(2) _ |> i(3) _

但最终的想法是,对于初学者来说,在中间插入参数可能不是最容易的事情。您可能会考虑,与采用其他工作流程相比,这是否是良好的编程习惯。

推荐阅读
郑谊099_448
这个屌丝很懒,什么也没留下!
DevBox开发工具箱 | 专业的在线开发工具网站    京公网安备 11010802040832号  |  京ICP备19059560号-6
Copyright © 1998 - 2020 DevBox.CN. All Rights Reserved devBox.cn 开发工具箱 版权所有