在上一篇 Javascript 闭包与高阶函数 ( 一 )中介绍了两个闭包的作用。 两位大佬留言指点,下来我会再研究闭包的实现原理和Javascript 函数式编程 。

今天接到头条 HR 的邮件,真是超级开心呐,希望熬过一个周后一切顺利 ~

这一篇,继续举一些闭包的常见例子 。

提取this

我们常常需要面临下面的业务场景

var push = Array.prototype.push;
var a = [];
push.call(a, 1);
console.log(a); // 1

这样固然可行,可是 我们有时候更想进行下面的操作

var a = [];
push(a, 1);
console.log(a); // 1

这应该怎么做呢? 思路就是将a 提取出来作为this,然后调用Array.prototype.push 方法 。

Function.prototype.uncharrying = function() {
var self = this; return function() {
var _this = Array.prototype.shift.call(arguments);
return self.apply(_this, arguments);
}
} var push = Array.prototype.push.uncharrying();
var a = [];
push(a, 1);
console.log(a);

函数节流

在很多业务场景中,比如 window.onresize 或者一些轮播图组件中,为了防止不断触发,都会使用一个函数节流的操作。下面看一个最简单的函数节流

var flag = false;

window.resize = function(e){
if(flag) {
return;
}
setTimeout(function(){
... // 业务逻辑代码 flag = false;
},1000);
flag = true;
}

这样做可用,但是缺点很多 。

下面用一个闭包将其包装起来 。

window.resize = (function(e){
var flag = false;
return function(){
if(flag) {
return;
}
setTimeout(function(){
... // 业务逻辑代码 flag = false;
},1000);
flag = true;
}
})();

看起来更加优优雅一点 。如果把节流的函数单独剥离呢??下面是完整代码

var throttle = function ( fn, interval ) { 

    var __self = fn,    // 保存需要被延迟执行的函数引用
timer, // 定时器
firstTime = true; // 是否是第一次调用 return function () {
var args = arguments,
__me = this; if ( firstTime ) { // 如果是第一次调用,不需延迟执行
__self.apply(__me, args);
return firstTime = false;
} if ( timer ) { // 如果定时器还在,说明前一次延迟执行还没有完成
return false;
} timer = setTimeout(function () { // 延迟一段时间执行
clearTimeout(timer);
timer = null;
__self.apply(__me, args); }, interval || 500 );
}; }; window.onresize = throttle(function(){
console.log( 1 );
}, 500 );

分时函数

与函数节流不同,分时函数用来限制函数调用的次数,用来提供页面性能 。

一个例子是创建 WebQQ的 QQ好友列表。列表中通常会有成百上千个好友,如果一个好友

用一个节点来表示,当我们在页面中渲染这个列表的时候,可能要一次性往页面中创建成百上千个节点。

在短时间内往页面中大量添加 DOM节点显然也会让浏览器吃不消,我们看到的结果往往就

是浏览器的卡顿甚至假死 。

这时候就需要分时函数,每隔一段时间运行一段 。

'use strict';

var timeChunk = function(argsAry, fn, count) {
var interval;
var exec = function() {
var l = argsAry.length;
for (var i = 0; i < Math.min(count || 1, l); i++) {
var arg = argsAry.shift();
fn(arg);
}
} return function() {
interval = setInterval(function() {
var flag = exec();
if (argsAry.length === 0) {
clearInterval(interval);
interval = null;
}
}, 500)
}
}; var a = [],func;
for (var i = 0; i < 36; i++) {
a.push(i);
} func = timeChunk(a, function(i) {
console.log(i);
}, 10)
func();

闭包和高阶函数的应用非常广泛,很多设计模式都是通过闭包和高阶函数来实现的 。

希望此文可以对你有帮助 。

转载请声明本文出处: http://www.cnblogs.com/likeFlyingFish/p/6426892.html

Javascript 闭包与高阶函数 ( 二 )的更多相关文章

  1. Javascript 闭包与高阶函数 ( 一 )

    上个月,淡丶无欲 让我写一期关于 闭包 的随笔,其实惭愧,我对闭包也是略知一二 ,不能给出一个很好的解释,担心自己讲不出个所以然来. 所以带着学习的目的来写一写,如有错误,忘不吝赐教 . 为什么要有闭 ...

  2. JavaScript之闭包与高阶函数(一)

    JavaScript虽是一门面向对象的编程语言,但同时也有许多函数式编程的特性,如Lambda表达式,闭包,高阶函数等. 函数式编程是种编程范式,它将电脑运算视为函数的计算.函数编程语言最重要的基础是 ...

  3. JavaScript ES6函数式编程(一):闭包与高阶函数

    函数式编程的历史 函数的第一原则是要小,第二原则则是要更小 -- ROBERT C. MARTIN 解释一下上面那句话,就是我们常说的一个函数只做一件事,比如:将字符串首字母和尾字母都改成大写,我们此 ...

  4. [Node.js] 闭包和高阶函数

    原文地址:http://www.moye.me/2014/12/29/closure_higher-order-function/ 引子 最近发现一个问题:一部分写JS的人,其实对于函数式编程的概念并 ...

  5. JavaScript进阶之高阶函数篇

    JavaScript进阶之高阶函数篇 简介:欢迎大家来到woo爷说前端:今天给你们带来的是JavaScript进阶的知识,接下来的系列都是围绕着JavaScript进阶进行阐述:首先我们第一篇讲的是高 ...

  6. Python 进程线程协程 GIL 闭包 与高阶函数(五)

    Python 进程线程协程 GIL 闭包 与高阶函数(五) 1 GIL线程全局锁 ​ 线程全局锁(Global Interpreter Lock),即Python为了保证线程安全而采取的独立线程运行的 ...

  7. 如何在JavaScript中使用高阶函数

    将另一个函数作为参数的函数,或者定义一个函数作为返回值的函数,被称为高阶函数. JavaScript可以接受高阶函数.这种处理高阶函数的能力以及其他特点,使JavaScript成为非常适合函数式编程的 ...

  8. javascript设计模式学习之三—闭包和高阶函数

    一.闭包 闭包某种程度上就是函数的内部函数,可以引用外部函数的局部变量.当外部函数退出后,如果内部函数依旧能被访问到,那么内部函数所引用的外部函数的局部变量就也没有消失,该局部变量的生存周期就被延续. ...

  9. 《JavaScript设计模式与开发实践》——第3章 闭包和高阶函数

    闭包 变量的作用域和生存周期密切相关 高阶函数 函数可以作为参数被传递 函数可以作为返回值输出

随机推荐

  1. X-004 FriendlyARM tiny4412 uboot移植之点亮指路灯

    <<<<<<<<<<<<<<<<<<<<<<<<< ...

  2. centos 上网问题

    前言:由于Linux下很多软件安装必须网络环境下进行,因此,对于如何在VMware下进行上网,我折腾了至少三天,今天上午,也即五一劳动节,终于搜到一遍技术文章,经过自己实践,VMware下Linux的 ...

  3. Memcached源码分析之items.c

    #include "memcached.h" #include <sys/stat.h> #include <sys/socket.h> #include ...

  4. VB.NET中网络编程所需组件WinHTTP的添加

    VB.NET中网络编程所需组件: WinHTTP组件:项目-->添加引用-->COM选项卡-->Microsoft WinHTTP Services,version 5.1--> ...

  5. 详解Objective-C的meta-class 分类: ios相关 ios技术 2015-03-07 15:41 51人阅读 评论(0) 收藏

    比较简单的一篇英文,重点是讲解meta-class.翻译下,加深理解. 原文标题:What is a meta-class in Objective-C? 原文地址:http://www.cocoaw ...

  6. java.lang.ClassNotFoundException: org.apache.commons.pool2.impl.GenericObjectPoolConfig

    问题描述: Caused by: org.springframework.beans.factory.BeanCreationException: Error creating bean with n ...

  7. 安卓组件-BroadcastReceiver

    [转]http://emilyzhou.blog.51cto.com/3632647/685387 一.BroadcastReceiver的简介 用于异步接收广播Intent,广播Intent的发送是 ...

  8. 编写PHP规则

    PHP是运行在服务器端的语言,可以动态生成html页面.这篇博客介绍它的一些编码规则. 一.基本规则 1.PHP代码总是用<?php和?>包围,例如 <?php echo " ...

  9. 笔记-Python基础教程(第二版)第一章

    第一章 快速改造:基础知识 01:整除.乘方 (Python3.0之前 如2.7版本) >>> 1/2 ==>0 1/2整除,普通除法: 解决办法1: 1.0/2.0  ==& ...

  10. IM 之 融云

    官方网站:http://www.rongcloud.cn 官方开发文档:http://www.rongcloud.cn/docs/ IM 融云 之 开发基础概念 IM 融云 之 通讯能力库API IM ...