xxleyi / learning_list

聚集自己的学习笔记
11 stars 3 forks source link

Beyond Closure in JS and Python #11

Open xxleyi opened 5 years ago

xxleyi commented 5 years ago

大部分人对闭包的掌握程度:

能面试的程度 中级 我们用的插件里有用闭包的地方,如果我看源码,我能看出来

为啥有闭包?就是为了能在别的地方调用b函数用到函数a里的变量 a包着b

定场鸡汤

不要刻意去记住某件事,而要去寻找使其显而易见的解释。 -- 理查德·费曼


changA 不传参

let a = {a: 3}

function changeA(){
  a = {a: "change"}
  }

changeA()
a = {'a': 3}

def changeA():
  a = {'a': "change"}

changeA()

JS Tutor 小演示

Python3 Tutor 小演示

xxleyi commented 5 years ago

changA 传参

let a = {a: 3}

function changeA(a){
  a = {a: "change"}
  }

changeA(a)
a = {'a': 3}

def changeA(a):
  a = {'a': "change"}

changeA(a)

JS Tutor 小演示

Python3 Tutor 小演示

xxleyi commented 5 years ago

Closure:


image

Environment Diagrams: visual tool to keep track of bindings and state of a computer program.

xxleyi commented 5 years ago

Python assumes that all variables in a function are local.

In Python local variable declaration is automatic/implicit while in JavaScript it is not (you have to use var or let or const).

xxleyi commented 5 years ago
var funcs = [];
for (var i = 0; i < 3; i++) {
  funcs[i] = function() {
    console.log("My value: " + i);
  };
}
for (var j = 0; j < 3; j++) {
  funcs[j]();
}

var funcs = [];

function createfunc(i) {
    return function() { console.log("My value: " + i); };
}

for (var i = 0; i < 3; i++) {
    funcs[i] = createfunc(i);
}

for (var j = 0; j < 3; j++) {
    funcs[j]();
}

JS Tutor Closure 演示

function f() {
    var result = [];
    for (var i of [0, 1, 2]) {
        result.push(function () { return i });
    }
    return result;
}

var result = f();

console.log(result[0](), result[1](), result[2]());

var result = []

function f() {
  let y = result.length;
  result.push(function () { return y });
}

f();
f();
f();

console.log(result[0](), result[1](), result[2]());

JS Tutor Closure 演示

xxleyi commented 5 years ago
# funcs = [];

# for i in range(3):
#     funcs.append(lambda: print("Myvalue: " + str(i)))

# for j in range(3):
#     funcs[j]()

funcs = [];

def createfunc(i):
    return lambda: print("Myvalue: " + str(i))

for i in range(3):
    funcs.append(createfunc(i))

for j in range(3):
    funcs[j]()

Python3 Tutor Closure 演示

def outer():
    result = []
    for i in range(3):
        def inner():
            return i
        result.append(inner)
    return result

result = outer()
print(result[0].__closure__)
print(result[1].__closure__)
print(result[2].__closure__)

print(result[0](), result[1](), result[2]())

# 另外一种形式
result = []
def outer():
    y = len(result)

    def inner():
        return y

    result.append(inner)

outer()
outer()
outer()

print(result[0].__closure__)
print(result[1].__closure__)
print(result[2].__closure__)

print(result[0](), result[1](), result[2]())

Python3 Tutor Closure 演示

xxleyi commented 5 years ago

Evaluation Model

环境模型干的事情:状态管理。 其数据结构不算复杂,就是一层层的 frame,每一层 frame 维护自己内部的映射关系,同时又有一个专门的link,指向自己所归属的 frame。

推荐文章:SICP Goodness - The Environment Model

xxleyi commented 5 years ago

作用域: The scope of a variable are the locations where it is accessible.

JS 和 Python 共通大概有:

JS 特有:

Python 特有(可能):

词法作用域:

xxleyi commented 5 years ago

environment & scope

强烈推荐一篇文章(文章成篇较早,没涉及 let const 语法,但丝毫不影响这些概念):Variables: Scopes, Environments, and Closures

xxleyi commented 5 years ago

应用举例:currying

let curriedAdd = a => b => a + b
let eleven = curriedAdd(5)(6)
console.log(eleven === 11)

// 进阶版
let curred2 = h => a => b => h(a, b)
let curriedAdd = curred2((a, b) => a + b)
let addFive = curriedAdd(5)
let eleven = addFive(6)
console.log(eleven === 11)

JS Tutor curry2 演示 推荐文章:Currying in JavaScript ES6

def curry2(h):
    def f(x):
        def g(y):
            return h(x, y)
        return g
    return f

make_adder = curry2(lambda x, y: x + y)
add_three = make_adder(3)
add_four = make_adder(4)
five = add_three(2)

# lambda expression
curry2 = lambda h: lambda x: lambda y: h(x, y)
make_adder = curry2(lambda x, y: x + y)
add_three = make_adder(3)
add_four = make_adder(4)
five = add_three(2)

Python3 Tutor curry2 演示

xxleyi commented 5 years ago

Python 中的 __closure__ 到底是个什么东西?

def outer():
    x = 100
    def inner():
        print(x)
    print(inner.__closure__)    # not None
    inner()

outer()

Python Tutor 演示

xxleyi commented 4 years ago

现在回头来看,价值依旧。