重点:什么是实参形参、实参求和、在函数内更改实参的值、
隐式添加return、递归
1.函数
数学里的函数:任意一个x的值 都会有一个确定的y与它对应 ; x:自变量; y:因变量
数学里的函数的值是确定的
而计算机里的函数(函数式编程) 的值是不确定的
- 耦合:代码重复的东西大多了
- 高内聚:开发的一个功能(模块)代码相关性强:紧密联系度强-->即高独立性-->即独立的完成一个任务
- 低耦合:把重复的代码提取出来-->组成一个独立的功能体(模块)-->去完成一个特点的功能
高内聚、低耦合:一个模块它有强的功能性、强的独立性,可以拿过去直接用
高内聚、低耦合 --> 模块的单一责任制:一个功能的代码只管这一块
解耦合:最好的方式就是函数,解耦合的方式都是基于函数的
2.最基本的函数写法:函数声明
为什么叫函数声明?因为用function来声明一个叫test的函数
基本格式:
function test(参数){
函数执行语句;
}
用:执行同样功能的语句,
var if(1>0){test();}
var if(2>0){test();}
var if(3>0){test();}
我们要完成的就是:当以上条件满足的时候分别去执行一个for循环输出0到9
直接拿过去用就行
function test(){
for(var i=0;i<10;i++){
console.log(i);
}
}
函数的功能都是提前准备好了的,
各个功能的函数就相当于含有各种功能的软件
安装软件的过程相当于编写函数的过程
3.匿名函数表达式
var test = function() { 函数执行语句; }
当用表达式定义函数时,后边的函数是匿名函数(因为后面没有test, 这样的函数没有名字)
这样函数定义的方式叫做匿名函数表达式,也叫函数字面量
var a=[] ,[]就是一个数组字面量
var a={} ,{}就是一个对象字面量,还有数字类型、字符串类型字面量等等
var test = function test1(){//声明了一个函数test1 将test1赋给test
a=1;
console.log(a);
// test1(); test1可以在函数内部执行,但是会无限循环
}
test();
test1(); /当上式test()函数执行的时候会默认忽略test1,即此句输出ReferenceError
}
test()函数执行的时候会默认忽略test1()
4.函数名的命名规则
和变量差不多:不能数字开头
可以含有数字 _ $
包含数字
小驼峰命名法
不能使用关键字、保留字等
5.函数的组成部分
function 函数名 参数(可不填) 、 返回值(可不填)如return后面括号内可不填
function test(){
var a=1,
b=2;
console.log(a+b);
}
test();/之前function test()括号内没有参数 即里面固定的值 不能赋值
function test(a,b){ /形参
console.log(a+b);
}
test(1,2);/之前function test()括号内有参数; 即可以赋值; 此句test()传达的值1,2称之为实参
第二个函数中a,b不用时占位,形式上调用,称之为形参
而下面test括号内的1,2 实际上调用 ,称之为实参
形参是占位符,实参是给占位符赋值
或者说形参就是变量,实参就是给变量赋值
区别在函数内部声明变量,无法在函数调用时赋值
小细节:
function test(a,b,c){
console.log(a,b,c);
}
test(1,2); /不会报错 输出1, 2, undefined
/c的类别是undefined
function test(a,b,c){
console.log(a+b+c);
}
test(1,2); /输出NaN 1 + 2+ undefined = 非数? 非数!
function test(a,b){
console.log(a,b);
}
test(1,2,3); /不会报错 输出1 , 2
总结:形参和实参数量可以不相等
6.实参与argument
在函数内部能知道有哪些实参吗?函数内部有个argument存储了实参
function test(a,b){
console.log(arguments); //输出argument数组 里面存了实参 1 2 3
console.log(arguments.length);/输出3
}
test(1,2,3);
面试知识点:实参求和
function sum(){
var a = 0;
for (var i=0;i<arguments.length;i++){
a = a + arguments[i]
}
console.log(a);
}
sum(1,2,3);
在函数内更改实参的值
- 实参和形参不是同一个变量,他们在函数内部是映射关系 形参和实参中任何一个变,另一个都会变。但如果没有形参就没有映射关系
function test(a,b){
a=3;/形参 a重新赋值为3
console.log(argumens[0]); /输出3 表明形参变实参也会变
arguments[0] = 2 /对第一个变量重新赋值
console.log(a);/表明实参变形参也会变
}
test(1,2);
/此例中argumens[0]和a = 3 不是一个东西; 形参a=3存在栈内存中 而argumens[0]的值存在堆内存中,然后栈内存中存地址
/形参和实参中任何一个变,另一个都会变
此例实用性:当用户填了个不合法的数时,自动更改它
- 当实参里面没有这个值时:
function test(a,b){
b=3;
console.log(argumens[1]); //输出undefined
/实参都没有b这个值,不能改变
}
test(1);
7.隐式添加return
1.每个函数最后一定是return,如果没写,js引擎会默认添加
2.如果写了return,那么return后面的语句是不会执行的(笔试细节):
function test(){
console.log('1');
return;
console.log('2');/不输出 /return下所有语句是不会被执行的 甚至是 return!
return("3"); /不输出
}
即出现return就直接结束整个循环
8.作用域
每个function都有自己独立的作用域
作用域:已声明的变量和函数可访问的范围
9.总结
函数式编程到底是什么? 其实就是一个固定的功能或者是程序段 被封装的过程。
实现一个固定的功能或者是程序需要什么? 在这个封装体中需要一个入口和一个出口,入口就是参数,出口就是返回
10.实战、递归
(1)定义一个函数,从wp接受一个饮料的名称,函数返回对应的价格
function drinks() {
var a = window.prompt('请输入饮料名称');
if (a == '可乐') {
console.log('cola');
} else if (a == '雪碧') {
console.log('sprite');
} else { console.log('暂无该饮料'); }
}
drinks();
(2)定义一个函数,从wp接受第一个数,接收一个运算符号(+ - * / %),接受第二个数,利用这个函数做运算,并返回运算结果
var a = Number(window.prompt('请输入第一个数'));
var b = window.prompt('请输入运算符');
var c = Number(window.prompt('请输入第二个数'));
function operation(a, b, c) {
if(b == "+"){
console.log(a+c);
}else if(b == "-"){
console.log(a-c);
}else if(b == "/"){
console.log(a/c);
}else if(b == '*'){
console.log(a*c);
}else{
console.log(a%c);
}
}
operation(a, b, c);
(3)定义一个函数,从wp接收一个n,算出n的阶乘,不能用for循环
/利用递归:
var a = Number(window.prompt('请输入一个数'));
function Factorial(a) {
if(a == 1){
return 1;
}
return a * Factorial(a - 1);
}
console.log(Factorial(a));
这题我本来想先用for循环解决,却遇到了一个问题:
var a = Number(window.prompt('请输入一个数'));
var sum = 1; //全局变量
function Factorial(a){
for(var i=1;i<= a;i++){
//var sum = sum * i;//返回NaN //因为我在这里重新声明(var)了sum 导致它不能访问外面的sum,而此时后面的sum没赋值,所以输出非数NaN
/解决办法 就是去掉var
sum = sum * i //这样才是对的
console.log(sum);
}
}
console.log(sum);
Factorial(a);
(4)定义一个函数,从wp 接收一个n, 算出斐波那契数列的第n位,不能用for循环
var n = window.prompt("输入n");
function fb(n){
if(n <= 2){
return 1;
}
if(n<=0){
return 0;
}
return fb(n-1) + fb(n - 2); /递归里面一般都用return
}
console.log(fb(n));
(5)递归
实战总结:递归总是走到出口(返回)的时候,再向上一步一步的返回结果;
递归就是函数自己调用自己,慎用,用for循环更好
递归的解决方法:1.找到计算的规律 2.找到一个递归的出口,让函数结束掉
常见问题FAQ
- 免费下载或者VIP会员专享资源能否直接商用?
- 本站所有资源版权均属于原作者所有,这里所提供资源均只能用于参考学习用,请勿直接商用。若由于商用引起版权纠纷,一切责任均由使用者承担。更多说明请参考 VIP介绍。
- 提示下载完但解压或打开不了?
- 找不到素材资源介绍文章里的示例图片?
- 模板不会安装或需要功能定制以及二次开发?
发表评论
还没有评论,快来抢沙发吧!