JavaScript 闭包&基于闭包实现柯里化和bind
闭包:
- 1 函数内声明了一个函数,并且将这个函数内部的函数返回到全局
- 2 将这个返回到全局的函数内中的函数存储到全局变量中
- 3 内部的函数调用了外部函数中的局部变量
闭包简述:
- 有权访问另一个函数局部作用域中的变量的函数
闭包清除:
- 将存储该内部函数的全局变量赋值为null,此时内部函数没有被引用,被垃圾回收机制回收
优点:
- 有私有变量存在
- 避免全局污染
- 防止私有变量被垃圾回收
缺点:
- 势必造成内存泄漏
示例:
function fn1() {
var a = 1;
function fn2(){
var b = 0;
a ++;
b++;
console.log(a,b);
}
return fn2;
}
var fns = fn1();
fns();
fns();//3,1
//第二次执行fns,fns又创建新的执行期上下文,此间b经历了残忍地再初始化和重建
//而a因为在fn2的局外,又为全局变量fns所庇佑,于是得以苟且偷生,并继续接下来的运算
function fn1(s){
var a = 1;
var o = {a:1};
return function(){
a++;
o.a++;
console.log(a,o.a);
}
}
var fn = fn1();
fn();
fn();
fn();
fn();//5,5
fn = null;//清除闭包
运用:
- curring
- bind
curring :
1 函数多行执行
/*
闭包实现柯里化 柯里化主要做两件事情:
1 执行函数参数个数不为0时,将参数列表用concat连接存储在数组arr中
2 否则执行参数列表为arr的执行函数
步骤:
1 在外部函数新建一个数组arr
2 当参数个数不为0时,arr在内部函数存储每次函数执行的参数列表,返回并用全局变量接收内部函数,形成闭包
3 当前执行函数的参数个数不为0时,将参数列表存进数组
4 当执行函数的参数个数为0时,执行参数列表为arr的执行函数
*/
function currying(fn) {
var arr = [];
return function () {
if (arguments.length > 0) {
// Array.from(arguments).forEach(item => arr.push(item));
//闭包,return的内部函数保有了外部函数变量
arr = arr.concat.apply(arr, arguments);
return;
}
return fn.apply(null,arr);//执行参数列表为arr的getSum函数
}
} function getSum() {
//执行的时候,将参数列表的参数归并求和
return Array.from(arguments).reduce(function (value, item) {
return value + item
});
}
//闭包,将返回的内部函数存储到全局变量
var fns = currying(getSum);
fns(1, 3, 5);
fns(2, 3, 5);
var sum = fns();
console.log(sum);
2 函数单行执行
function currying(fn) {
var arr = [];
return function () {
if (arguments.length > 0) {
arr = Array.from(arguments).concat.apply(arr, arguments);
return arguments.callee;//因为是单行执行,执行完一次需要返回此函数去执行下个参数列表
}
//参数列表为0,执行函数
return fn.apply(null, arr);
}
}
function getSum() {
return Array.from(arguments).reduce((value, item) => {
return value + item;
});
}
var fns = currying(getSum);
var sum = fns(1,1,1)(1,1,1)();
console.log(sum);
执行结果:

bind:
/*
实现bind:
将函数中的this指向绑定到bind函数的参数中
用apply实现
*/
function bind(fn, obj) {
return function () {
//这里的传参要看是谁调用
console.log(arguments);//3,5,这里的参数是setTimeout传进来的
fn.apply(obj, arguments);
}
}
function abc(_a, _b) {
this.a = _a;
this.b = _b;
}
var obj = {};
setTimeout(bind(abc, obj), 200, 3, 5);//执行function(){abc(3,5)}
JavaScript 闭包&基于闭包实现柯里化和bind的更多相关文章
- 浅析 JavaScript 中的 函数 currying 柯里化
原文:浅析 JavaScript 中的 函数 currying 柯里化 何为Curry化/柯里化? curry化来源与数学家 Haskell Curry的名字 (编程语言 Haskell也是以他的名字 ...
- swift 学习(二)基础知识 (函数,闭包,ARC,柯里化,反射)
函数 func x(a:Int, b:Int) {} func x(a:Int, b:Int) -> Void {} func x(a:Int, b:Int) ->(Int,Int ...
- Scala 基础(十二):Scala 函数式编程(四)高级(二)参数(类型)推断、闭包(closure)、函数柯里化(curry)、控制抽象
1 参数(类型)推断 参数推断省去类型信息(在某些情况下[需要有应用场景],参数类型是可以推断出来的,如list=(1,2,3) list.map() map中函数参数类型是可以推断的),同时也可以 ...
- 温故而知新:柯里化 与 bind() 的认知
什么是柯里化?科里化是把一个多参数函数转化为一个嵌套的一元函数的过程.(简单的说就是将函数的参数,变为多次入参) const curry = (fn, ...args) => fn.length ...
- 一道javascript面试题(闭包与函数柯里化)
要求写一个函数add(),分别实现能如下效果: (1)console.log(add(1)(2)(3)(4)()); (2)console.log(add(1,2)(3,4)()); (3)conso ...
- JavaScript 反柯里化
浅析 JavaScript 中的 函数 uncurrying 反柯里化 柯里化 柯里化又称部分求值,其含义是给函数分步传递参数,每次传递参数后部分应用参数,并返回一个更具体的函数接受剩下的参数,这中间 ...
- 浅析 JavaScript 中的 函数 uncurrying 反柯里化
柯里化 柯里化又称部分求值,其含义是给函数分步传递参数,每次传递参数后部分应用参数,并返回一个更具体的函数接受剩下的参数,这中间可嵌套多层这样的接受部分参数函数,直至返回最后结果. 因此柯里化的过程是 ...
- JavaScript中的反柯里化
转载自:https://www.cnblogs.com/zztt/p/4152147.html 柯里化 柯里化又称部分求值,其含义是给函数分步传递参数,每次传递参数后部分应用参数,并返回一个更具体的函 ...
- JavaScript函数柯里化
函数式 JavaScript是以函数为一等公民的函数式语言.函数在JavaScript中也是一个对象(继承制Function),函数也可以作为参数传递成函数变量.最近几年函数式也因为其无副作用的特性. ...
随机推荐
- [MC] 我的世界 craftbukkit-1.12.2 卡爆
昨天晚上的时候,和朋友玩我的世界 结果我这边卡爆了,牛圈里面的牛都是一动一动的... 然后我登陆服务器,发现CPU爆炸了... 100%的使用率 mstsc都卡爆了 内存占用了800多MB (服务器是 ...
- DOJ1187 : 重建家园 (分数规划 && 二分 && kruskal)
最优答案一定是一颗树 那么二分比值,不断kruskal找到最大可以满足的解就可以了 代码如下 #include <cstdio> #include <algorithm> us ...
- 【C语言】用C语言输出一个吃豆人
大圆盘减去扇形和小圆盘: #include <math.h> #include <stdio.h> int main() { double x, y; ; y >= -; ...
- [USACO13JAN]Cow Lineup
Description Luogu3069 USACO Solution 由于两个点之间最多可以有\(k+1\)种牛,而牛的种数是单调的.所以可以用尺取法(区间伸缩法),每次右移右端点后,让左端点不断 ...
- springboot引入Oracle依赖
最近学习spring boot,在网上找一些项目学习,有的项目引入了oracle驱动包,自己搭建一直不成功,百度发现说是权限问题无法下载. 然后参考下面博客终于解决:springboot引入Oracl ...
- 空字符串(“”)和null和空格字符串(" ")的区别
1.类型 null表示的是一个对象的值,而并不是一个字符串.例如声明一个对象的引用,String a = null ;""表示的是一个空字符串,也就是说它的长度为0,但它是一个字符 ...
- 把jar包部署为linux服务
一直未配置成功,直到放弃后reboot了下,才直到错的不是自己的配置,而是自己不懂 1.在touch /etc/rc.d/init.d/tl_c_cons_service(创建新文件) 2.vi /e ...
- 吴裕雄 python 机器学习——支持向量机SVM非线性分类SVC模型
import numpy as np import matplotlib.pyplot as plt from sklearn import datasets, linear_model,svm fr ...
- Python - CentOS 下用 yum 安装 pip
1. 概述 python 安装完成 发现后续需要一个 python 自己的 包管理工具 书上说默认会装, 然后我发现还是没有 命令执行的结果我就不给了, 这个判断起来, 应该是没有太大难度的 2. 环 ...
- 【Python爬虫程序】抓取MM131美女图片,并将这些图片下载到本地指定文件夹。
一.项目名称 抓取MM131美女写真图片,并将这些图片下载到本地指定文件夹. 共有6种类型的美女图片: 性感美女 清纯美眉 美女校花 性感车模 旗袍美女 明星写真 抓取后的效果图如下,每个图集是一个独 ...