【问题标题】:When to use closures in swift? [closed]何时在 swift 中使用闭包? [关闭]
【发布时间】:2015-04-23 13:11:14
【问题描述】:

我已经进行了几个月的 ios 开发,并渴望在我的编程模式中实现新事物。

现在我正在学习闭包,对它的语法知之甚少,知道它可以用来代替委托进行回调。以及在一些 UIViewAnimation 和排序中实现它。

但我真的想知道它的用途,即在我们的基本编程中我们应该在哪里使用闭包。就像我们想将信息从孩子发送给父母时使用委托一样。所以任何可以在我们日常快速编程中使用的解释或简短示例都会有所帮助?

谁能告诉我这些闭包实际上是如何计算值的

reversed = sorted(names, { (s1: String, s2: String) -> Bool in return s1 > s2 } )

在这些示例中,名称和闭包作为方法的参数..但这实际上是如何计算的?

你能解释一下在这个动画代码中传递闭包时这些是如何工作的吗:

UIView.animateWithDuration(duration: NSTimeInterval, 
    animations: (() -> Void)?, 
    completion: ((Bool) -> Void)?)

我真的想知道流程?

【问题讨论】:

    标签: ios swift closures


    【解决方案1】:

    Swift 中最常用的两种情况是完成块和高阶函数。

    完成块:例如,当您有一些耗时的任务时,您希望在该任务完成时收到通知。您可以为此使用闭包,而不是委托(或许多其他东西)

    func longAction(completion: () -> ()) {
        for index in veryLargeArray {
            // do something with veryLargeArray, which is extremely time-consuming 
        }
        completion() // notify the caller that the longAction is finished 
    }
    
    //Or asynch version
    func longAction(completion: () -> ()) {
    
        dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0)) {
    
            for elem in veryLargeArray {
                // do something with veryLargeArray, which is extremely time-consuming
            }
            dispatch_async(dispatch_get_main_queue(), { 
                completion() // notify the caller that the longAction is finished 
            })
        }
    }
    
    longAction { print("work done") }
    

    在上面的示例中,当您有一个耗时的任务时,您想知道 for 循环何时完成对非常大的数组的迭代。您将闭包 { println("work done") } 作为函数的输入参数,该函数将在 for 循环完成其工作后执行,并打印“工作完成”。而发生的事情是你给longAction一个函数(闭包)并命名为completion,当你在longAction中调用completion时,这个函数就会被执行。

    高阶函数:您可以使用闭包作为高阶函数的输入参数,例如:

    let array = [1, 2, 3]
    let smallerThanTwo = array.filter { $0 < 2 }
    

    这样,你可以过滤掉小于2的数字。

    更新关于sorted(可能)如何工作:

    所以这个想法是, sorted 将遍历数组,并将两个连续的元素 (i, i + 1) 相互比较,并在需要时交换它们。 “如果需要”是什么意思?您提供了闭包{ (s1: String, s2: String) -&gt; Bool in return s1 &gt; s2 },如果s1lexiographically 大于s2,它将返回true。如果该闭包返回truesorted 算法将交换这两个元素,并将其与接下来的两个元素(i + 1,i + 2,如果未到达数组末尾)进行计数。所以基本上你必须为sorted 提供一个闭包,它会告诉“何时”交换元素。

    【讨论】:

    • 我对此略知一二。你能举个关于完成块的例子吗?
    • @copeME 我用一个例子更新了我的答案。
    • @copeME 我更新了我的答案,解释了排序可能如何工作。
    • 感谢让我更清楚的人
    • 我希望有一个简单的闭包示例用作完成块...
    【解决方案2】:

    闭包类似于:

    { (params) -> returnType in
      statements
    }
    

    以下是 Apple doc 使用它的一些原因

    • 从上下文推断参数和返回值类型
    • 单表达式闭包的隐式返回
    • 简写参数名称
    • 尾随闭包语法

    【讨论】:

    • 你能给我一个很好的例子,说明如何使用闭包作为完成块并描述它是如何在那里发生的吗?
    【解决方案3】:
    1. 与其他函数相比,通常闭包没有名称。这意味着当您想要将代码块传递给某个函数而不将该代码包装到命名方法中时,可以在每种情况下使用它们。排序是最流行的例子。

    2. 闭包可以在其边界之外使用变量。所谓的“捕获价值”

    【讨论】:

      猜你喜欢
      • 2015-05-26
      • 2017-03-17
      • 2018-03-03
      • 2015-10-08
      • 1970-01-01
      • 1970-01-01
      • 2014-07-25
      • 2014-08-09
      • 1970-01-01
      相关资源
      最近更新 更多