博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
JavaScript中的函数
阅读量:5173 次
发布时间:2019-06-13

本文共 3423 字,大约阅读时间需要 11 分钟。

一、函数是对象

js中的函数都是Function的实例,有自己的属性和方法。因此函数名也只一个指向函数对象的指针,并不是绑定的。

View Code
二、函数声明与函数表达

Js中声明都会被提到代码的最前面,而赋值则会执行到所在代码行才会进行。

console.log(sum(1,2));//3function sum(num1,num2){  return num1+num2;      }console.log(anothersum(1,2));//unexpected identifiervar anothersum=function(num1,num2){  return num1+num2;  }

所以在sum声明前调用sum函数不会出错,而在anothersum前调用anothersum就会出错。

同样变量的声明与赋值也有类似的规则。不过js中的变量没有作用域这个概念。即在一个函数内for语句中声明的变量在整个函数内都可以访问得到。

三、作为值和参数的函数  

因为ECMAScript中的函数名本身就是变量,所以函数也可以当作值来使用。

做为参数传递:

1 var arr=[1,2,3,11,55,6,13];2 function compare(num1,num2){3     return num1-num2;4 }5 arr.sort(compare);6 console.log(arr);

同样的道理,js中的函数也可以做为值返回。如:

1 function compare(proName){ 2     return function(object1,object2){ 3         var val1=object1[proName]; 4         var val2=object2[proName]; 5         if(val1
val2){ 8 return 1; 9 }else{10 return 0;11 }12 };13 }14 var data=[{name:'Zhang',age:'28'},{name:'Nicholas',age:'29'}];15 data.sort('name');16 console.log(data[0].name);//Nicholas17 data.sort('age');18 console.log(data[0].age);//Zhang

另外js中函数的参数传递实际上值的传递,对于对象并不是引用传递,传递的只是一个地址。

四、函数内部的属性

在Js的函数中,有两个特殊的属性arguments与this。其中arguments是一个类数组对象,包含所有实际传入的参数,但这个对象一个callee的发生,始终指向拥有这个arguments的函数。而this由运行时的环境决定是window对象,还是某一个对象的值。

arguments.callee的用法(经典阶乘函数):

1 function factorial(num){2     if(num<=1){3         return 1;4     }else{5         return num*arguments.callee(num-1);6     }7 }8 console.log(factorial(4));//24

如果不用arguments.callee指向拥有这个arguments的函数,而使用函数名,会有什么情况出现呢?当你修改了函数名的指向时,就会出现错误。

1 function factorial(num){ 2     if(num<=1){ 3         return 1; 4     }else{ 5         return num*factorial(num-1); 6     } 7 } 8 console.log(factorial(4));//24 9 factorialNew=factorial;10 factorial=function(num){11     return 0;12 }13 console.log(factorial(4));//014 console.log(factorialNew(4));//0

函数内部的this:this的值引用的是执行环境对象。

1 var obj={2     color:'red'3 };4 var color='blue';5 function showColor(){6     console.log(this.color);7 }8 showColor();//blue9 showColor.call(obj);//red

因为第一次调用showColor()是在全局环境中执行,所以this值为window,而第二次调用call把this变为obj这个对象。

五、函数的属性和方法

因为js中的函数是对象,所以函数也有属性和方法。

函数的length属性,代表函数实际希望传入的参数的个数。

1 function sayName(name){2     var name=name||'nothing';3     console.log(name,arguments.length);4 }5 sayName('k');//k 16 sayName();//nothing 07 console.log(sayName.length);//1

可以使用argumets.length==arguments.callee.length是否相等来判断期望传递的参数的个数与实际传递的参数是否相等。

caller属性:保存着调用当前函数的函数的引用。

1 function outer(){2     inner();3 }4 function inner(){5     console.log(arguments.callee.caller);6 }7 outer();//function outer(){inner();}

 

prototype属性:

对于js中引用类型来说,prototype是保存实例方法的真正所在。也就是说valueOf()和toString()等方法实际上都存在于prototype名下。同一个类的所有实例共享prototype中的属性。prototype与js实例继续,创建类有关。详见下一篇博文。

apply()和call()。这两个方法的用途是在特定的作用域下调用函数,实际上等于设置函数体内this的值。

apply()方法接收两个参数,一个是运行函数的作用域,另一个是数组,可以是Array实例,也可以是arguments。

1 function sum(num1,num2){2     return num1+num2;3 }4 function callsum(num1,num2){5     console.log(sum.apply(this,arguments));//36     console.log(sum.apply(this,[num1,num2]));//37 }8 callsum(1,2);

call()与apply()类似,第一个参数是运行函数的作用域,其余参数直接传递就行。

1 function sum(num1,num2){2     return num1+num2;3 }4 function callsum(num1,num2){5     console.log(sum.call(this,num1,num2));//36 }7 callsum(1,2);

如果只有第一个参数,call()与apply()没有区别。

使用call()和apply()方法扩充作用域的最大好处是对象不需要与以一奉百任何的耦合关系。

在ECMAScript5中也可以使用bind()方法。

转载于:https://www.cnblogs.com/zhouyongtao/archive/2012/11/19/2776776.html

你可能感兴趣的文章
2017.4.18-morning
查看>>
ACE6.3.3在Linux(CentOS7.0)下的安装和使用
查看>>
面试准备
查看>>
mysql 1067
查看>>
java之接口适配器
查看>>
nginx安装手册
查看>>
动态将ASPX生成HTML网页并将网页导出PDF
查看>>
Find Backpacker Jobs in Australia
查看>>
面试题:return和finally执行
查看>>
Heroku第三方服务接入指南(二)
查看>>
MSRA专访摘要
查看>>
团队作业4
查看>>
随手一写,简单的四则运算练习
查看>>
第四次团队作业--选题
查看>>
记录专用
查看>>
一句实现jquery导航栏
查看>>
从零开始学 Web 之 Ajax(五)同步异步请求,数据格式
查看>>
场景分析:用户登录界面场景分析
查看>>
条形码生成包 BarCodeToHTML.cs(以颜色为背景的完整版)(下载的完整版)
查看>>
数据库事务的四大特性以及事务的隔离级别
查看>>