闭包如何捕获值?

How does the closure capture values?

我post一个关于关闭的问题,但它被保留为搁置

现在我想更详细、更具体。这条线是如何工作的?

    let names = ["Chris", "Alex", "Ewa", "Barry", "Daniella"]
    func backwards(s1: String, s2: String) -> Bool {
        return s1 > s2
    }
   var reversed = sorted(names, backwards)

当我将函数作为 argument.How 传递时,它是否从名称数组中获取值?

你应该看看the documentation,但这里有一个示例排序函数(选择排序,因为这是最简单的):

func selectionSort<T>(inout array: [T], comparator: (T,T) -> Bool) {
    var min: Int

    for n in 0..<array.count {
        min = n

        for x in (n + 1)..<array.count {
            if comparator(array[x], array[min]) {
                min = x
            }
        }

        if min != n {
            let temp = array[min]
            array[min] = array[n]
            array[n] = temp
        }
    }
}

selectionSort(&names, backwards)

如您所见,该函数使用闭包来检查顺序,调用闭包的确切次数取决于 sorted 函数的实现。

大多数 Java 脚本开发人员即使在多个地方使用闭包,也会卡在闭包中。有很多博客讲解Closure。我浏览了大部分博客,并决定尽可能使其更简单。 以一种非常简单的方式,我可以说 Closure 是一个函数,它具有定义它的变量的内存。

示例 1:

function increment(i){  
    return function(){
        return i++;
    }
}

var increase_1 = increment(5); //passing a reference or scope variable 5

//increase_1 store value of i as 5 in memory
increase_1()                            //5
increase_1()                            //6
increase_1()  

                      //7

再举个简单的例子 示例 2:

add(3,5);
add(3)(5);

现在我需要一个可以执行两个表达式的函数....

function add(a,b){
  if(arguments.length===2){
    return a+b;
  } else {
   return function(b){
      return a+b;
    }    
  }
}

示例:3:

// A typical example
function addLinks () {
    for (var i=0, link; i<5; i++) {        
        link = document.createElement("a");
        link.innerHTML = "Link " + i;     
        link.onclick = function(){
         console.log(i);
        }
        document.body.appendChild(link);
    };   
}
addLinks();

//这将输出什么。 当你执行它时,它会创建一个 link,点击它会打印一些值。 那么它在单击 link1 时打印的值是多少。想一想……我知道,一开始你会感到困惑。 是的,它打印 5。 不仅点击这个特定的 link,而且点击每个 link,它会给你 5。 所以,现在我想打印 0,1,2,3,4。是的,当我点击 link0 时,它打印 0,在 link1 上,它打印 1,依此类推。 现在,我想让你仔细检查示例 1 并尝试以相同的方式实现并尝试记住一些自执行 annonmys 函数的东西。

function addLinks () {
    for (var i=0, link; i<5; i++) {        
        link = document.createElement("a");
        link.innerHTML = "Link " + i;     
        link.onclick = function(c){
          return function(){
            console.log(c);
          }
        }(i);//passing a reference 
        document.body.appendChild(link);
    };   
}

addLinks();

因此,如果您仔细观察此示例,当事件处理程序与 link 绑定时,将传递引用或范围。 这与实施 jQuery 的方式相同。