zoukankan      html  css  js  c++  java
  • 函数

    callee
    arguments对象有一个名为callee的属性,callee属性是一个指针,指向拥有这个arguments对象的函数。
    比较经典的阶乘例子:

    function factorial(num){
      if(num <= 1){
        return 1;
      }else{
        return num * factorial(num - 1);
      }
    }

    上述例子用到了递归,和函数名factorial紧密耦合到一起,可以使用arguments.callee解耦。

    function factorial(num){
      if(num <= 1){
        return 1;
      }else{
        return num * arguments.callee(num - 1);
      }
    }

    caller
    函数对象属性caller保存着调用当前函数的函数引用。如果在全局作用域中调用当前函数,它的值为null.

    function outer(){
      inner();
    }
    function inner(){
      alert(inner.caller);
    }
    outer();

    以上代码会导致警告框显示outer()函数的源代码。因为outer()调用inner(),所以inner.caller就指向了outer()。为了实现更松散的耦合,可以通过arguments.callee.caller来访问相同点信息。

    function outer(){
      inner();
    }
    function inner(){
      alert(arguments.callee.caller);
    }
    outer();

    函数的属性和方法

    在ECMAScript中函数也是对象,因此函数有属性和方法,每个函数都有2个属性:length和prototype。其中,length表示函数希望接收的参数的个数,如下例:

    function sayName(name){
      console.info(name);
    }
    function sum(num1, num2){
      return num1 + num2;
    }
    function sayHi(){
      console.info("hi");
    }
    console.info(sayName.lenth);     // 1
    console.info(sum.length);      // 2 
    console.info(sayHi.length);      // 0

    prototype

    对于ECMAScript中的引用类型来说,prototype是保存它们所有实例方法的真正所在。如toString()和valueOf()等方法实际上都保存在prototype名下,只是通过各自对象的实例访问。在创建自定义引用类型以及实现继承时,prototype属性是非常重要的。prototype是不可枚举的,所以不能使用for-in。

    call()apply()方法

    每个函数都包含2个非继承而来的方法:apply()和call()。这2个方法的用途都是在特定的作用域中调用函数,实际上等于设置函数体内this对象的值。

    一、apply()方法接收2个参数:一个是在其运行函数的作用域,另一个是参数数组。参数数组可以是Array实例,也可以是arguments对象。

    function sum(num1, num2){
      return num1 + num2;
    }
    function callSum1(num1, num2){
      return sum.apply(this,arguments);
    }
    function callSum2(num1, num2){
      return sum.apply(this,[num1,num2]);
    }
    console.info(callSum1(10,10));    //20
    console.info(callSum2(10,10));    //20

    callSum1和callSum2函数传入this(这里实际上是window,因为这两个函数是在全局作用域中调用的)作为this的值。

    二、call()方法和apply()方法的作用相同,它们区别只在于接收参数的方式不同,对于call()来说,第一个this值没有变化,变化的是其余参数都直接传递给参数。就是将传入的参数逐个列出来。

    function sum(num1, num2){
        return num1 + num2;
    }
    function callSum(num1, num2){
        return sum.call(this, num1, num2);
    }
    console.info(callSum(10,10));    //20

    call()和apply()方法的强大之处不是传递参数,而是能够扩充函数赖以运行的作用域。看下面的例子

    window.color = "red";
    var o = {color:"blue"};
    function sayColor(){
        console.info(this.color);
    }
    sayColor();                //red
    sayColor.call(this);      //red    
    sayColor.call(window);    //red
    sayColor.call(o);         //blue
  • 相关阅读:
    NHibernate之映射文件配置说明
    JS jQuery json日期格式问题的办法
    Spring.net 配置说明
    NHibernate常见问题及解决方法
    Could not load type 'System.Web.Mvc.ViewPage<dynamic>' in asp.net mvc2 after publishing the website
    启用SQLite的Data Provider 运行WECOMPANYSITE时遇到ERROR CREATING CONTEXT 'SPRING.ROOT': ERROR THROWN BY A DEPENDENCY OF OBJECT 'SYSTEM.DATA.SQLITE'
    Nuget 命令 NuGet 管理项目库
    vs2013(vs2015) 打开vs2010 找不到此项目类型所基于的应用程序 MVC2 升级 MVC5 不能加载Web项目
    JsonResult作为Action返回值时的错误
    MVC 数据验证
  • 原文地址:https://www.cnblogs.com/chenxiaocai/p/5543546.html
Copyright © 2011-2022 走看看