Scala 中方法、函数和部分应用函数的函数组合

发布于 2024-12-08 18:06:32 字数 1263 浏览 0 评论 0原文

有点类似于 Stack Overflow 问题Compose 和 andThen 方法,我一直在研究 Twitter 的 Scala学校教程,很快就遇到了评论者遇到的同样问题(这很好,因为我上床睡觉时以为我的问题已经解决了)。

在本教程中,它定义了两个方法:

def addUmm(x: String) = x + " umm"
def addAhem(x: String) = x + " ahem"

在较新版本的 Scala 中,您无法像这样调用它们的 compose:addUmm(_).compose(addAhem(_)),接受的答案(以及其他一些答案似乎取决于这样一个事实:addUmm 和 addAhem 是方法,而不是函数,这在尝试调用 compose 时会产生问题。我满意地去睡觉了,成功了run:

scala> ((s: String) => s + " umm").compose((s: String) => s + " ahem")
res0: String => java.lang.String = <function1>

很酷。问题是,虽然无法编写方法是有道理的,但当我对我知道的值执行相同的操作时,它会计算为 Function1:

val a = (s: String) => s + " umm"
val b = (s: String) => s + " ahem"
val c = a(_).compose(b(_))

好吧,最后一行会出现与原始问题确实如此,尽管这次它们是函数的部分应用,而不是方法。原始问题中的答案之一(排名很高,但不是公认的答案)似乎暗示它与如何有关。 解释是什么?

部分应用被扩展,对于a的 Scala 新手,事实上,无论您是否在两个地方显式指定 _: String ,推理器都会出错 a(_).compose(b(_)) ,但是 < code>a.compose(b) 确实有点令人困惑。

Somewhat similar to Stack Overflow question Compose and andThen methods, I've been working through Twitter's Scala School tutorial and quickly ran into the same problem that a commenter had (which was great, because I went to bed thinking my problem was solved).

In the tutorial, it defines two methods as such:

def addUmm(x: String) = x + " umm"
def addAhem(x: String) = x + " ahem"

and while in newer versions of Scala, you can't call compose on them as such: addUmm(_).compose(addAhem(_)), the accepted answer (and some of the other answers seem to hinge upon the fact that addUmm and addAhem are methods, not functions, which creates an issue when trying to call compose. I went to bed satisfied, having successfully run:

scala> ((s: String) => s + " umm").compose((s: String) => s + " ahem")
res0: String => java.lang.String = <function1>

Cool. The issue is that while not being able to compose methods makes some sense, when I the same thing with values I know evaluate to Function1:

val a = (s: String) => s + " umm"
val b = (s: String) => s + " ahem"
val c = a(_).compose(b(_))

Well, that last line coughs up the same error that the original question did, even though they're partial applications of functions this time, not methods. One of the answers in the original question (highly-ranked, but not the accepted answer) seems to hint that it has to do with how the partial application is expanded, what is the explanation?

For a Scala newbie, the fact that the inferencer gets a(_).compose(b(_)) wrong no matter if you explicitly specify _: String both places, but a.compose(b) does is somewhat confusing.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

装迷糊 2024-12-15 18:06:32

a(_).compose(b(_)) 扩展为 x =>; { a(x).compose(y => b(y) }。因此出现错误。您想要的是 (x => a(x)).compose(y => b(y)) 添加一对括号可以解决此问题,

scala> (a(_)).compose(b(_: String))
res56: String => java.lang.String = <function1>

scala> res56("hello")
res57: java.lang.String = helloahemumm

但由于 ab 是函数,因此您可以避免所有这些麻烦,只需执行 <代码>a组成b。

a(_).compose(b(_)) expands to x => { a(x).compose(y => b(y) }. Hence the error. What you want is (x => a(x)).compose(y => b(y)). Adding a pair of parentheses fixes this.

scala> (a(_)).compose(b(_: String))
res56: String => java.lang.String = <function1>

scala> res56("hello")
res57: java.lang.String = helloahemumm

But since a and b are functions, you can avoid all this cruft and simply do a compose b.

梦里泪两行 2024-12-15 18:06:32

您可以简单地使用“a compose b”。

scala> val c = a compose b
c: String => java.lang.String = <function1>

You can use simply 'a compose b'.

scala> val c = a compose b
c: String => java.lang.String = <function1>
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文