3.1 函数的作用
封装多条语句,在任何地方,任何时候调用执行,简化代码书写
3.2 函数的声明
字面量方式定义
使用function声明,后跟一组参数以及函数体
语法:
function 函数名 (参数1,参数2...)
{
函数内容
}
var赋值表达式定义
给一个变量声明时赋值个函数
var 变量名/函数名 =function(参数)
{
函数内容
}
构造函数定义
通过new运算符声明,较为繁琐不建议使用
var add = new Function('参数1','参数2','...');
元素的id声明函数
设置id触发后进入函数
预解析
- 如果使用字面量方式定义,调用函数放在声明前面或者后面都可以。
- 如果使用赋值表达式声明,调用函数只能放在声明之后
- 全局作用域中的预解析会率先寻找作用域中开头的“ function ”和“ var ”关键字,将function提前定义出来,将var定义为undefined,所以赋值表达式只会预解析出来undefined,而不是函数内容。
其他说明:
1. 函数名属于标识符
2. 参数可有无可,非必须
3.3函数定义的位置
- 全局作用域下的函数在整个代码中几乎都能调用
- 同一作用域内函数(同一级函数)之间能互相调用
在fn3内找不到,只能在fn同级或者add内找到
- JS中没有块级作用域,if或者for只是个代码块,内部函数定义并不在一个级内,不宜使用
这里不能实现判断后再定义函数,因为if只是代码块,function在内部仍然会被预解析到。除非:
这里可以实现是因为首先“var 变量=undefined”预解析之后再执行判断就没问题了
3.4 函数的调用
语法:
函数名(参数1,参数2...)
普通调用
效果就是浏览器弹出警告框
结果如此:
对象中的函数的调用
需要说明sex这个函数在哪个对象内
匿名函数的调用
赋值给一个变量进行调用
匿名函数不能直接使用,因为他没有名字,所以需要给var出的一个变量,让变量得到这个函数
直接调用自执行
必须赋值给一个变量的原因是,如果不赋值给一个变量,function开头,预解析会认为这是个函数定义而不是调用,这样就可以定义后就直接调用
或者:
用括号将整个function语句包起来,这样就不是function开头了,同理,在function前面加“+” “*” “!”这类合法符号都可以,相当于骗预解析程序“穿上马甲就不认识了”
递归调用
类似于C语言中的递归算法
对象内方法调用
正常调用
这里是对点击操作进行了赋值函数,这里的调用是默认的
函数名不正常调用
首先要给函数名$带单引号,然后在调用时使用“对象名+['函数名']”的方法调用
如果函数名合法,就可以使用“ . ”调用 如果函数名合法,就需要使用“[ ' ' ]”调用
链式调用
可以一句话多次调用对象中函数
需要给被调用函数添加return:this属性,意为被调用后指向上一级(operation)
间接调用
call方法和apply方法,可以通过this借用别的对象中的方法
call方法
这里的this原本指向person对象,后面的call方法可以改变指向
apply方法
传递参数通过数组形式,其实只有两个数组,第一个是this指向位置,第二个是所有参数装进一个数组,适合传进来的参数为数组
3.5 函数的返回值
与C语言基本相同
- 函数会在执行完return后立刻停止然后退出,可以用于结束函数功能
- 返回值可以为变量也可以为空,用于提前停止函数执行又不需要返回的情况
举个栗子:
结果如下:
什么可以做返回值
字符串,数字,undefined,布尔值,数组(一次性返回多个值),对象(直接返回带属性名的对象就行),函数...
3.6 函数中的参数
实参与形参
大概与C语言相通
实参个数<形参个数,优先将实参赋值给前面的形参,没有赋值结果为 undefined
实参个数>形参个数,将多余实参舍弃
什么可以做参数
数字,字符串,undefined,null,数组,对象,函数...
数组:each[1,2,3],function(index,item)index是参数个数,item是参数值
对象:each[name:'asd',sex:'man'],function(index,item)index是name和sex,item是asd和man
这样不按顺序的输入参数
arguments对象
JS中的函数实参会形成一个类数组,而arguments就是访问这个类数组的,本质是一个对象
- 与数组类似,并不是array的实例
- [ ]语法访问他的单个元素
- length属性确定传递参数的个数
- 尽量不对arguments进行操作
arguments.callee
arguments.callee指函数本体,多用在递归中
举个栗子:
修改递归函数时不用处理内部函数名,更加便捷(但是严格模式不允许)
但是可以采用赋值定义中的后一部分(小名,反正平时用不到)
栗子1:
输出arguments的长度
栗子2:
这里通过位置访问第2个元素
栗子3:
这里给两个参数的函数只输入一个参数,打印第二个参数,第二个参数打印出来是undefined,不存在
栗子4:
在非严格模式中
尽管函数的第一个参数为10,但是在函数内给第一个参数赋值为5,所以打印出来也是5
3.7 多个语句综合求平均值
经过三次输入内容结果如下:
3.8 多函数模块化
求1000以内既是质数又是完数的数字:
分别写两个判断函数,最后
3.9 延时函数
语法:
setTimeout(参数名,数字(单位毫秒))
刷新之后,过三秒输出“123”
- 一个函数被使用后,局部变量会被销毁
- 函数的优点之一是方便修改和维护