先介绍一下js中的高阶函数,所谓的高阶函数就是,一个函数中的参数是一个函数或者返回的是一个函数,就称为高阶函数。

  js中已经提高了一下高阶函数,使用起来非常棒,当然我们也可以自己实现,我介绍几种ES5/ES6新增的数组函数。

  首先是forEach,forEach它接受两个参数,第一个函数,第二个传一个this引用对象(可以不传),函数支持传3个参数第一个表示遍历的当前值,第二个为索引,第三个表示当前对象。

[1,2,4,5].forEach(function(item,index){
  console.log(item,index);
})

  模拟forEach的实现

Array.prototype.for = function(fn){
  for(var i=0;i<this.length;i++){
    fn(this[i],i);
  }
};
[2,3,4,5,6].for(function(item,index){
  console.log(item,index);
})

  map返回处理过后的一个新数组

var arr = [1,2,3,4,5];
var a = arr.map(function(item,index){
  if(index>0){
    return item*index;
  }
  return item;
})

console.log(a); //[1, 2, 6, 12, 20]
console.log(arr); //[1, 2, 3, 4, 5]

  模拟实现map

var arr = [1,2,3,4,5];
Array.prototype.m = function(fn){
  var arr = [];
  for(var i=0;i<this.length;i++){
    arr.push(fn(this[i],i,this));
  }
  return arr;
};
console.log(arr.m(function(item,index,thisValue){
  console.log(thisValue); //[1, 2, 3, 4, 5]
  if(item>3){
    return item;
  }
  return item-1;
})) //[0, 1, 2, 4, 5]

  

  some方法用于检测数组中的元素是否满足指定条件,如果有一个元素满足条件,则表达式返回true , 剩余的元素不会再执行检测,如果没有满足条件的元素,则返回false。

Array.prototype.so = function(fn){
  for(var i=0;i<this.length;i++){
    if(fn(this[i],i,this)){
      return true;
    };
  }
  return false;
};

var arr = [1,2,3,4,5,6];

console.log(arr.so(function(item){
  return item>7;
}))

  filter返回满足条件的值,是一个新数组。

Array.prototype.f = function(fn){
  var arr = [];
  for(var i=0;i<this.length;i++){
    fn(this[i],i,this)&&arr.push(this[i]);
  }
  return arr;
};
var arr = [1,2,3,4,5,6];
console.log(arr.f(function(item){
  return item<2;
}))

  every检测数组所有元素是否都符合指定条件,如果数组中检测到有一个元素不满足,则整个表达式返回 false ,且剩余的元素不会再进行检测。

Array.prototype.ev = function(fn){
  for(var i=0;i<this.length;i++){
    if(!fn(this[i],i,this)){
      return false;
    };
  }
  return true;
};

var arr = [1,2,3];

console.log(arr.ev(function(item){
  return item>1;
}))

函数柯里化

  简单来说就是某些情况下我们执行某个函数,并不需要它直接返回一些值给我们,而是再我们需要的时候它再给我们返回,这就是函数柯里化,以下是某位大牛写的。

一个 currying 的函数首先会接受一些参数,接受了这些参数之后,该函数并不会立即求值,而是继续返回另外一个函数,刚才传入的参数在函数形成的闭包中被保存起来。待到函数被真正需要求值的时候,之前传入的所有参数都会被一次性用于求值。

不完全柯里化版

var fn = (function(){
  var num = 0;
  return function(){
    if(arguments.length===0){
      return num;
    }else{
      for(var i=0;i<arguments.length;i+=1){
        num+=arguments[i];
      }
    }
  };
}())

fn(2);
fn(2,2,2);
fn(2);
console.log(fn()); //10

柯里化版

var currying = function(fn){
var arrNum = [];
  return function(){
    if(arguments.length===0){
      return fn.apply(this,arrNum);
    }else{
      [].push.apply(arrNum,arguments);
      return arguments.callee;
    }
  };
}

var count = (function(){
  var num = 0;
  return function(){
    for(var i=0;i<arguments.length;i+=1){
      num+=arguments[i];
    }
    return num;
  };
}());

var s = currying(count);
s(3);
s(3,3,3);

console.log(s());

函数反柯里化unCurrying
创建一个应用范围更广的函数。使本来只有特定对象才适用的方法,扩展到更多的对象。

简单版

var obj = {
"length": 3,
"0": 1,
"1": 2,
"2": 3
};

// Array.prototype.push.call(obj,3);
// console.log(obj);

function push(){
  var a = [].shift.call(arguments);
  Array.prototype.push.apply(a,arguments);
};
push(obj,3);
push(obj,30);
push(obj,'js');
console.log(obj);

也可以这样。

var obj = {
"length": 3,
"0": 1,
"1": 2,
"2": 3
};

// Array.prototype.push.call(obj,3);
// console.log(obj);

Function.prototype.uncurrying = function(){
  var _this = this; //Array.prototype.push
  return function(){
    //删除第一个,并且返回 obj
    var obj = [].shift.call(arguments);
    //obj调用Array.prototype.push方法,传递arguments,注意此时arguments已经没有包含obj这个参数了。
    return _this.apply(obj,arguments);
  };
};

var push = Array.prototype.push.uncurrying();

console.log(push(obj,'666'));
console.log(obj)
push(obj,'777');
console.log(obj)

Javascript函数中的高级运用的更多相关文章

  1. Javascript函数中传递带空格的参数

    通常在页面中要让某些内容点击后产 生点击事件(非页面跳转)都会使用onclick,但是这样不适于需要传递参数的情况,于是写成直接调用Javascript函数的方式:<a href=javascr ...

  2. 在JavaScript函数中使用EL表达式注意的事项

    最近在使用JSP显示从Servlet带过来的数据时,大量的使用到了EL表达式,并且有些EL表达式是在使用到JavaScript的函数时作为参数传入的,举个例子,比如下面的样子: 这个HTML标签的意思 ...

  3. JavaScript函数中的参数(arguments)

    arguments argument是JavaScript中的一个关键字,用于指向调用者传入的所有参数. function example(x){ alert(x); alert(arguments. ...

  4. javascript函数中的三个技巧【二】

    技巧二: [惰性载入函数] 因为浏览器之间的行为的差异,我们经常会在函数中包含了大量的if语句,以检查浏览器特性,解决不同浏览器的兼容问题,比如,我们最常见的为dom节点添加时间的函数 functio ...

  5. javascript函数中with的介绍

    /*js函数中with函数的用法分析定义 方便用来引用某个对象中已有的属性但是不能用来给对象添加属性 要给对象创建新的属性 必须明确的引用该对象*/代码格式with(object) statement ...

  6. javascript函数中变量重名

    <script type="text/javascript"> function fun(a){ console.log(a); // function var a=1 ...

  7. javascript函数中的三个技巧【三】

    技巧三: [函数绑定] 在javascript与DOM交互中经常需要使用函数绑定,定义一个函数然后将其绑定到特定DOM元素或集合的某个事件触发程序上,绑定函数经常和回调函数及事件处理程序一起使用,以便 ...

  8. javascript函数中的三个技巧【一】

    在学习javascript中,函数是非常重要的,现在我来谈谈对函数的理解以及在工作和用法中的一些技巧 技巧一. [作用域安全的构造函数] 构造函数其实就是一个使用new操作调用的函数 function ...

  9. 随笔:JavaScript函数中的对象----arguments

    关于arguments 调用函数时,如果需要传参,其实参数就是一个数组,在函数体的内置对象arguments可以访问这个数组,如: arguments[0]:第一个参数 arguments[1]:第二 ...

随机推荐

  1. checked属性

    使用checked属性,你可以设置复选按钮和单选按钮默认被选中. 为此,只需在input元素中添加属性checked <input type="radio" name=&qu ...

  2. [Python] Removing a non-empty folder

    Removing a non-empty folder You will get an ‘access is denied’ error when you attempt to use os.remo ...

  3. ExtJs 3.0 动态生成 CheckBox

    在开发过程中,往往需要利用数据动态生成Checkbox.如权限节点.考试答案,调查选项等等.在Extjs中,有两种方法来获取后台数据,一是Ext.Ajax()方法,第二种是利用 Store,store ...

  4. 【转】linux shell实现随机数多种方法(date,random,uuid)

    在日常生活中,随机数实际上经常遇到,想丢骰子,抓阄,还有抽签.呵呵,非常简单就可以实现.那么在做程序设计,真的要通过自己程序设计出随机数那还真的不简单了.现在很多都是操作系统内核会提供相应的api,这 ...

  5. jdk1.6 webService 客户端代码生成和测试

    参数:测试webService的地址:http://10.113.11.1:9090/enocpService/buildingEngService?wsdl 1,eclipse中新建一个项目, 2, ...

  6. MySQL 升级详细步骤 (包括 Percona)

    MySQL 升级步骤 MySQL 5.1.72 升级到 MySQL 5.5.36 鉴于我在升级的时候遇到的麻烦问题,我觉得有必要把一些细节说清楚,免得引起误解了.感觉官方文档上的升级步骤写的比较简单, ...

  7. \(\S1\) 描述性统计

    在认识客观世界的过程中,统计学的思想和方法经常起着不可替代的作用.在许多工程及自然科学的专业领域中,包括可靠性分析.质量控制.生物信息.脑科学.心理分析.经济分析.金融风险管理.社会科学推断.行为科学 ...

  8. Linux 安装Weblogic12 - copy

    # groupadd weblogic# useradd -g weblogic weblogic# passwd weblogic# mkdir -p /var/bea# chown -R webl ...

  9. Fedora23Server配置

    系统准备 启动网卡: sudo service network start 更新系统: sudo dnf update 远程管理: https://IP:9090/ Dnf使用: http://www ...

  10. 每周一书-《Bootstrap基础教程》

    首先说明,本周活动有效时间为8月15日到21日.本周为大家送出的书是有电子工业出版,贺臣/陈鹏编著的<Bootsrap基础教程>,为前端入门必读书籍. 下面是从书中摘录的内容. “ Boo ...