Swift相当于Ruby的“yield”

时间:2016-02-08 22:52:01

标签: ruby swift

我是Swift的新手,拥有Ruby背景。我想知道我是否有办法做这样的事情:

def completion_handler response, &block
  yield response
end

extracted = proc {|r| puts r}

completion_handler "response", &extracted
response
=> nil

我在搜索方面有点麻烦,因为yield主要是调出序列生成器而我认为这不是我现在正在寻找的东西。我大多想知道这是否可行,因为有时候我希望能够将块提取到proc对象。在Swift中,闭包对我来说看起来像块。对proc对象有类似的提取吗?

2 个答案:

答案 0 :(得分:5)

Swift闭包大多与Ruby Lambdas非常相似。它们是具有一组定义的参数的对象,这些参数返回到它们的调用范围(不同于非对象Ruby Blocks或Ruby Procs,它们不检查参数计数以及return可以逃避调用范围的地方)。

因此,没有真正的yield等价物。接受闭包参数的Swift函数使用括号参数列表显式调用闭包。

答案 1 :(得分:3)

可以在变量中保存块(或“快捷编程指南”中的“闭包”)或传递它们。与ruby有很大区别的是,某些类型必须指定编译。

示例代码(仅使用swift 2.2-dev linux进行测试):

func foo(arg1: Int, block: ((Int)->(String))? = nil) {
    if let block = block {
        // ruby's yield (call the block with argument and get its return value)
        // is not part of swift grammar, so we have to call it manually.
        print(block(arg1))
    }
}

// named closure
let block1 = {(a: Int)->String in
    print("yielded", a)
    return "returned from block1"
}

foo(1, block: block1)

// unnamed closure
foo(2, block: {
    print("yielded", $0)
    return "returned from block2"
})

// unnamed closure in another syntax. usable only when the closure is the last argument.
foo(3) {
    print("yielded", $0)
    return "returned from block3"
}

输出:

yielded 1
returned from block1
yielded 2
returned from block2
yielded 3
returned from block3