码迷,mamicode.com
首页 > 其他好文 > 详细

函数Function

时间:2016-04-20 13:18:14      阅读:178      评论:0      收藏:0      [点我收藏+]

标签:

    函数实际上是对象,每个函数都是Function类型的实例,而且都与其他引用类型一样具有属性和方法。由于函数是对象,因此函数名实际上也是一个指向函数对象的指针,不会与某个函数绑定。

一、定义函数的方法:

1.函数声明

function sum(num1,num2){}

2.函数表达式

var sum=function(num1,num2){}

使用函数表达式定义时,没有必要使用函数名,但也可以是var sum=function ab(num1,num2){}

使用不带圆括号的函数名是访问函数指针,而非调用函数。

3.区别

解析器会率先读取函数声明,并使其在执行任何代码之前可用;至于函数表达式,则必须等到解析器执行到它所在的代码行,才会真正被解释执行。

 

二、函数没有重载

JS中函数没有重载,在创建第二个函数时,实际上覆盖了第一个函数。

 

三、作为值得函数

函数本身就是变量,所以函数也可以作为值来使用。可以像传递参数一样把一个函数传递给另一个函数,而且也可以将一个函数作为另一个函数的结果返回。

 

四、函数内部属性

1.arguments

在函数体内可以通过arguments对象来访问这个参数数组,从而获取传递给函数的每一个参数。arguments对象和数组类似,因此可以通过方括号访问,length确定传递进来的参数个数。arguments[0]

另外arguments的值永远与对应命名参数的值保持同步。

function doAdd(num1,num2){

  arguments[1]=10;

  alert(arguments[0]+num2);//num2每次都被重写为10

}

这个对象还有一个属性callee,该属性是一个指针,指向拥有这个arguments对象的函数。

function factorial(num){

  if(num<=1){

    return 1;

  }else{

    return num*arguments.callee(num-1);

  }

}

 

2.另一个函数对象的属性caller

这个属性保存着调用当前函数的函数的引用,如果是在全局作用域中调用当前函数,它的值为null。

function outer(){

  inner();

}

function inner(){

  alert(inner.caller);//弹出调用inner的函数的引用,也就是outer,因此会输出function outer(){inner();}

}

为了实现更松的耦合,可以这样调用

function inner(){

  alert(arguments.callee.caller);

}

 

五、函数的属性和方法

每个函数都包含两个属性length和prototype; length属性表示函数希望接受的命名参数的个数。

function sayName(num1,num2){}

alert(sayName.length)//2

prototype是保存函数所有实例方法的真正所在。不可枚举,无法使用for-in发现。

每个函数都包含两个非继承而来的方法:apply()和call()

用途:在特定的作用域中调用函数,实际上等于设置函数体内this对象的值。

扩充函数赖以运行的作用域。

1.apply()

接收两个参数:一个是在其中运行函数的作用域,另一个是参数数组。第二个参数可以是Array的实例,也可以是arguments对象。

2.call()

作用同apply,区别仅在于接收参数的方式不同。第一个参数相同,第二个参数是直接传递给函数,也就是说传递给函数的参数必须逐个列举出来。

3.bind()

其this值会被指定给传给bind()函数的值。

window.color=‘red‘;

var o={color:‘blue‘};

var b={color:‘yellow‘};

function sayColor(){

  alert(this.color);

}

var osaycolor=sayColor.bind(o);

var bsaycolor=sayColor.bind(b);

osaycolor()//‘blue‘

bsaycolor()//‘yellow‘

4.toLocalString()  toString() valueOf()

始终返回函数的代码。

 

六、理解apply() call()

经常会这样定义:
  function cat(){
  }
  cat.prototype={
    food:"fish",
    say: function(){
      alert("I love "+this.food);
    }
  }

var newCat = new cat();
newCat.say();

但是如果我们有一个对象newDog = {food:"bone"},我们不想对它重新定义say方法,那么我们可以通过call或apply用newCat的say方法:
newCat.say.call(newDog);
cat.prototype.say.call(newDog);

所以,可以看出call和apply是为了动态改变this而出现的,当一个object没有某个方法,但是其他的有,我们可以借助call或apply用其它对象的方法来操作。

用的比较多的,通过document.getElementsByTagName选择的dom 节点是一种类似array的array。它不能应用Array下的push,pop等方法。我们可以通过:
var domNodes = Array.prototype.slice.call(document.getElementsByTagName("*"));
这样domNodes就可以应用Array下的所有方法了。
 

call和apply可以用来重新定义函数的执行环境,也就是this的指向。通过一个操作DOM的例子来理解。

function changeStyle(attr, value){
    this.style[attr] = value;
}
var box = document.getElementById(‘box‘);
window.changeStyle.call(box, "height", "200px");

call中的第一个参数用于指定将要调用此函数的对象,在这里,changeStyle函数将被box对象调用,this指向了box对象,如果不用call的话,程序报错,因为window对象中没有style属性。
apply的用法:

window.changeStyle.apply(box, [‘height‘, ‘200px‘]);
 
1. 

function add(a,b)  

{  

    alert(a+b);  

}  

function sub(a,b)  

{  

    alert(a-b);  

}  

add.call(sub,3,1); //  4

 

2.

function Animal(){
  this.name = "Animal";
  this.showName = function(){
    alert(this.name);
  }
}

function Cat(){
  this.name = "Cat";
}

var animal = new Animal();
var cat = new Cat();

//通过call或apply方法,将原本属于Animal对象的showName()方法交给对象cat来使用了。
animal.showName.call(cat,",");   //Cat
//animal.showName.apply(cat,[]);  //Cat

 

3.实现继承

function Animal(name){
  this.name = name;
  this.showName = function(){
    alert(this.name);
  }

  this.hi=function(){// 注意这里必须是this引用才能继承,否则cat.hi()时,会报错,hi不是一个函数 

    alert("hello "+this.name);

  }
}

function Cat(name){
  Animal.call(this, name);
}

var cat = new Cat("Black Cat");
cat.showName();//Black Cat

cat.hi();//hello Black Cat

 

4.多重继承

function Class10(){

  this.showSub = function(a,b){
    alert(a-b);
  }
}

function Class11(){

  this.showAdd = function(a,b){
    alert(a+b);
  }
}

function Class2(){

  Class10.call(this);
  Class11.call(this);
}

var c2=new Class2();

c2.showSub(10,3)//7

c2.showAdd(10,3)//13

 

函数Function

标签:

原文地址:http://www.cnblogs.com/YangqinCao/p/5411758.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!