首页 > 代码库 > 《JavaScript设计模式与开发》笔记 6.高阶函数
《JavaScript设计模式与开发》笔记 6.高阶函数
- 1.函数作为参数传递
- 1.回调函数
- 2.Array.prototype.sort
- 2.函数作为返回值输出
- 1.判断数据的类型
- 3.高级函数的实现AOP
- 4.高阶函数的其他应用
- 1.currying 函数柯里化
- 2.uncurring
- 3.函数节流
- 4.分时函数
- 5.惰性加载函数
1.函数作为参数传递
1.回调函数
最经常用的或许就是异步Ajax了
var getUserInfo = function(userId,callback){ $.ajax("http://xxx.com/getUserInfo?"+userId,function(data){ callback(data); });}getUserInfo(14157,function(data){ alert(data.userName);});
2.Array.prorotype.sort
var array = [1,2,4];array.sort(function(a,b){ return b-a;});console.log(array);
2.函数作为返回值输出
1.判断数据的类型
场景
var isString = function(obj){ return Object.prototype.toString.call(obj) == ‘[object string]‘;}var isArray = function(obj){ return Object.prototype.toString.call(obj) ==‘[object Array]‘;}var isNumber = function(obj){ return Object.prototype.toString.call(obj) == ‘[Object Number]‘};以上代码可写成:var isType = function(type){ return function(obj){ //函数作为返回值进行返回 return Object.prototype.toString.call(obj) === ‘[object ‘+type+‘]‘; }}var isString = isType(‘String‘);var isArray = isType(‘Array‘);var isNumber = isType(‘Number‘);console.log(isString([1,2,3,4]));3.高级函数的实现AOPFunction.prototype.before=function(beforefn){ var _self = this; //这里的this实际上是func的this return function(){ //这个this是before 的this beforefn.apply(this,arguments); //这个是函数 return _self.apply(this,arguments); //func函数 }}Function.prototype.after=function(afterfn){ var _self = this; //这里的this实际上是func的this return function(){ var ret = _self.apply(this,arguments); //func函数 实际上func可以包含before函数函数 //这个this是after 的this afterfn.apply(this,arguments); //这个是函数 return ret; }}var func = function(){ console.log(‘2‘);}var asdf = func.before(function(){ console.log(‘1‘);}).after(function(){ console.log(‘3‘);});asdf();
流程图
3.高阶函数其他应用
1.函数柯里化 currying函数
currying又称部分求值,一个currying的函数首先会接受一些参数,接受了这些参数之后,该函数并不会立即求值,而是继续返回另外一个函数,刚才传入的参数在函数形成的闭包中被保存起来。带到函数真正需要求值的时候,之前传入的所有参数都会被一次性用于求值。
var currying = function(fn){ var args = []; return function(){ if(arguments.length == 0){ var Mynameisbalabala; return fn.apply(this,args); //不要被这个this迷惑,实际是将argus传递给cost进行计算 //return fn.apply(Mynameisbalabala,args); }else{ [].push.apply(args,arguments); return arguments.callee; //返回该函数 } }};var ASF2FASD = (function(){ var money = 0; return function(){ for(var i=0;i<arguments.length;i++){ money +=arguments[i]; } return money; }})();var ASDFA = currying(ASF2FASD);console.log(ASDFA(100).toString());/* ASDF(100) 返回 ==(return fn.apply(this,args))function (){ if(arguments.length == 0){ var Mynameisbalaba; return fn.apply(this,args); //不要被这个this迷惑,实际是将argus传递给cost进行计算 //return fn.apply(Mynameisbalaba,args); }else{ [].push.apply(args,arguments); return arguments.callee; //返回该函数 } }*/ASDFA(100);//ASDFA(100);//ASDFA(300);//console.log(ASDFA()); //600
2.uncurrying函数
在JavaScript中,当我们调用对象的某个方法时,其实不用关心该对象原本是否设计为拥有这个方法,这是动态类型语言的特点
,也是常说的鸭子类型的意思。
我们常用call和apply可以把任意对向当做this传入某个方法,这样一来,方法中用到this的地方就不在局限与原来规定的对象,而是加以泛化并得到更广的适用性。那么有没有把泛化this的过程提取出来呢....
仔细看一下代码还是很简单的不注解了.....
Function.prototype.uncurrying = function(){ var self = this;//此时是Array.prototype.push return function() { var obj = Array.prototype.shift.call(arguments); //obj是{ //‘length‘:1, //‘0‘:1 //} //arguments 对象的第一个元素被截取 return self.apply(obj,arguments); //相当于 Array.prototype.push.apply(obj,2); }}var push = Array.prototype.push.uncurrying();var obj = { "length":1, "0":1}push(obj,2);console.log(obj);
除了这样方法下面代码也是uncurrying的另一个实现方式:【】
Function.prototype.uncurrying = function(){ var self = this; return function(){ // Function.prototype.call { ‘0‘: 1, length: 1 } return Function.prototype.call.apply(self,arguments); //self =>asdfasdfasdfasdf对象 这里的this的话应该是push }}var push = Array.prototype.push.uncurrying();var asdfasdfasdfasdf = { "length":1, "0":1}push(asdfasdfasdfasdf,2);console.log(asdfasdfasdfasdf);
3.函数节流
函数调用频率过高,非常消耗性能的情况下使用函数节流比如监视窗口浏览器大小,比如监视鼠标的移动效果
实现节流:
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‘);},1000);
4.分时函数
<!DOCTYPE html><html lang="en"><head> <meta charset="UTF-8"> <title>Title</title></head><body></body><script> var timeout = function(ary,fn,count){ console.log(‘5‘); var obj, t; var len = ary.length; var start = function(){ for(var i=0;i<Math.min(count || 1,ary.length);i++){ var obj = ary.shift(); fn(obj); } }; return function(){ console.log(‘1‘); t = setInterval(function(){ if(ary.length === 0){ return clearInterval(t); } start(); },1000); }; }; var ary = []; for(var i=1;i<=1000;i++){ ary.push(i); }; var renderFriendList = timeout(ary,function(n){ var div = document.createElement("div"); div.innerHTML = n; document.body.appendChild(div); },8); renderFriendList();</script></html>
5.惰性加载函数
<!DOCTYPE html><html lang="en"><head> <meta charset="UTF-8"> <title>Title</title></head><body><div id="div1">点击我绑定事件</div></body><script> var addEvent = function(elem,type,handler){ if(window.addEventListener){ addEvent = function(elem,type,handler){ elem.addEventListener(type,handler,false); } }else if(window.attachEvent){ addEvent = function(elem,type,handler){ elem.attachEvent(‘on‘+type,handler); } } addEvent(elem,type,handler); } var div = document.getElementById(‘div1‘); addEvent(div,‘click‘,function(){ alert(‘1‘); }) addEvent(div,‘click‘,function(){ alert(‘2‘); })</script></html>
《JavaScript设计模式与开发》笔记 6.高阶函数
声明:以上内容来自用户投稿及互联网公开渠道收集整理发布,本网站不拥有所有权,未作人工编辑处理,也不承担相关法律责任,若内容有误或涉及侵权可进行投诉: 投诉/举报 工作人员会在5个工作日内联系你,一经查实,本站将立刻删除涉嫌侵权内容。