首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >将闭包数组缩减为单个闭包

将闭包数组缩减为单个闭包
EN

Stack Overflow用户
提问于 2020-05-09 16:40:03
回答 1查看 67关注 0票数 0

假设我有一个闭包数组,这些闭包可以彼此组合(例如,自同态,它们的输入和输出类型是相同的)。如何将这些闭包组合成一个单独的闭包?

作为参考,我试图设计如下的东西。

代码语言:javascript
复制
struct MyType {
    typealias MyClosure: (T) -> T
    private var myClosures: [MyClosure] = [ ... ]
    public var closure: MyClosure {
        get {
            return ? // somehow compose all of myClosures into a single closure here
        }
    }
}

我的第一个想法是使用reduce,àla myClosures.reduce(STARTING) { a, b in b(a) },但这需要提供一个初始值,然后依次对其应用闭包。我不想将闭包应用于任何东西(目前为止),而只是将闭包的私有列表合成成一个单独的公开闭包,可以在以后应用。考虑到reduce的定义方式,我希望这看起来像

代码语言:javascript
复制
myClosures.reduce(identity) { a, b in compose(a, b) }

func identity(_ input: T) { return input }

func compose(a: MyClosure, b: MyClosure) -> MyClosure { return b(a) }

但是b(a)的类型是T,而不是(T) -> T。如何才能做到这一点?这是一个更好的方式来进行闭幕式构图吗?

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2020-05-09 16:57:07

编辑:我最初的回答误解了你的问题所在。但鉴于我最初的答案可能对未来的读者有用,我会把它放在最下面。

您的compose函数就快到了!b(a)不编译,因为MyClosure不使用另一个MyClosureb(a)正在调用闭包(“函数应用程序”)。不是构图。既然compose返回一个闭包,为什么不返回一个闭包呢?在Swift中,典型的闭包如下所示:

代码语言:javascript
复制
{ (param) in return doSomethingTo(param) }

所以让我们把它还回去!

代码语言:javascript
复制
return { (x) in return b(a(x)) }

这可以简化为:

代码语言:javascript
复制
{ b(a($0)) } // "return" can be omitted as well!

此页 (以及其他事情)告诉您如何以及何时可以简化闭包语法。

原来的答案:

在这里使用reduce是正确的选择。还原操作是组合操作,所以让我们首先编写一个compose函数:

代码语言:javascript
复制
func compose<T>(_ x: @escaping (T) -> T, _ y: @escaping (T) -> T) -> (T) -> T {
    { y(x($0)) } // or { x(y($0)) } if you want it the other way
} 

然后,我们reduce。身份是什么?身份是具有以下属性的东西:

代码语言:javascript
复制
compose(identity, anything) == anything
compose(anything, identity) == anything

这是什么功能?身份函数!

所以我们得到:

代码语言:javascript
复制
func reduceClosures<T>(_ closures: [(T) -> T]) -> (T) -> T {
    closures.reduce({ $0 }, compose)
}
票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/61700254

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档