首页 > 解决方案 > 没有大括号和参数标签的匿名函数?

问题描述

我在另一个问题上看到了一些代码,它似乎用一些不寻常的语法创建了一个匿名函数(闭包表达式):

let plus: (Int, Int) -> Int = (+)

我理解左边——它声明了一个类型的常量(Int, Int) -> Int(一个接受两个整数并返回一个整数的函数)。但什么是(+)?它如何声明一个没有大括号的函数,以及当没有任何类型的参数标签时它如何引用两个参数?

该函数接受两个参数,将它们相加,然后返回结果。如果我用+不同的操作符(比如 a *)替换操作符,操作就会改变。那么它是某种速记{$0 + $1}吗?如果是这样,这个速记背后的逻辑是什么?

标签: swiftlambdaanonymous-functionshorthand

解决方案


实际上,这不是简写。

plus是一个类型的变量(Int, Int) -> Int。您可以将任何属于此类型(或其任何子类型)的对象分配给它。文字 lambda 闭包当然属于这种类型,但实际上命名函数或方法也可以。这正是这里正在发生的事情。

它正在将命名的运算符方法对象分配给+变量。

在语言指南的闭包章节中隐含地提到了这一点:

运算符方法

实际上有一种更的方法来编写上面的闭包表达式。Swift 的String类型将其大于运算符 ( >) 的特定于字符串的实现定义为具有两个 type 参数String并返回 type 值的方法Bool。这与方法所需的方法类型完全匹配sorted(by:)。因此,您可以简单地传入大于运算符,Swift 会推断您想要使用其特定于字符串的实现:

reversedNames = names.sorted(by: >)

因此,代码所做的是将Operator Method+分配给变量plus+只是分配给变量的函数的名称。不涉及魔术速记。

看到这个你会惊讶吗?

let plus: (Int, Int) -> Int = foo

推荐阅读