16.JavaScript函数、return陷阱、函数定义、参数传递、默认参数、局部变量、全局变量、返回值、技巧
文章目录
- 函数
- 函数的定义
- 局部变量
- 外部变量
- 内外变量重名
- 参数
- 参数默认值
- 年长代码的默认参数
- 空值合并运算符的应用
- 返回值
- return陷阱
- 小技巧
函数
在编程过程中,我们经常需要在很多地方使用一段相同的代码。例如,用户的注册、登录、注销和退出代码段,经常在不同的网页页面上存在。
在每次用到这些功能时都重新写一遍代码无疑是笨拙的,这种时候我们就可以使用函数。
函数可以将一段代码封装成一个代码块,并为这段代码起个名字(函数名),每当需要使用这段代码时,只需要提供函数名称就可以了。
函数一旦写成,就可以被无限次调用,而不需要重复的写代码。
实际上,我们在之前的每节课程都在使用函数,例如:alert()
、prompt()
、confirm()
等。
这些函数都是JavaScript
为了我们方便使用自带的函数,我们也可以创建自己的函数。
在很多情况下,我们会把函数称作“方法”,函数和方法通常都是混用的,二者本质上没有什么分别。
函数的定义
函数定义需要使用一个新的关键字function
,函数定义的语法规则如下:
function funcName(para1,para2,para3,...){//函数体
}
function
关键字会告诉JavaScript
引擎,这段代码的意义是创建一个函数,函数的名称是funcName
,然后括号中的是参数列表,{}
中的内容是函数体。
举个例子:
//函数定义的时候不执行
function pow(a,b){let temp = a;while(--b){a *= temp;}console.log(a);
}
以上代码创建了一个名为pow
的函数,这个函数可以计算 a b a^b ab。行数在定义的时候不会执行,只有在调用的时候才会执行。
例如,我们计算 2 3 2^3 23,在定义pow
函数后,就可以简单的使用pow(2,3)
实现,如下图:
提醒,这里的幂函数计算方法
pow
并不完善,例如当b=-1时就会死循环
如果我们需要的指数计算较多,就可以重复调用pow
函数,例如:
//函数定义
function pow(a,b){let temp = a;while(--b){a *= temp;}console.log(a);
}
//函数调用
pow(2,3)//2的3次方
pow(3,4)//3的4次方
pow(4,5)//4的5次方
执行结果如下:
这个案例清楚的演示了函数的最主要用途之一,即避免代码重复。
局部变量
局部变量就是定义在函数{}
内部的变量,这些变量只能在函数内部才能使用。
例如,上节课中
for
语句里面的变量i
举个例子:
function doSomething(a,b){let val = prompt('请输入点什么',0);console.log(val);
}
doSomething();
alert(val);//ERROR,这里不能使用val
执行结果如下:
由于变量val
是在函数内部定义的,只能在函数内部使用,外部不能使用函数内部定义的变量。
外部变量
虽然,函数体外不能访问函数体内部定义的变量,但是反过来,函数体内部是可以访问函数体外部定义的外部变量的。
举个栗子:
let val = prompt("请输入点什么",9);
function doSomething(){console.log(val);//使用函数体外的变量没有问题
}
doSomething();
代码执行结果如下:
用户输入的时候,输入了9
内外变量重名
如果内部变量和外部变量具有相同的名字,那么会优先使用内部变量。
举个栗子:
let num = 1;
function doSomething(){let num = 2;console.log(num);//这里使用的是内部变量
}
doSomething();
代码执行结果:
如果一个变量声明在所有函数之外,那么这个变量就是全局变量
程序中声明过多的全局变量不利于程序的优化执行
参数
函数体内部并非完全自治的,很多情况下还是需要一定的输入才能开始执行函数体代码,这个输入就是参数。
举个例子:
function bless(name,senc){console.log(`祝${name}${senc}`)
}
代码执行结果:
上例中我们为行数bless
传入了两个参数,分别是人名name
和祝福词senc
,这样就可以像任何人祝福任何话了。
如果我们在函数体内部修改变量,那么外部的变量是否会对应的变化呢?
举个例子:
let a = 1;
let b = 2;
function exchange(a,b){let temp = a;a = b;b = temp;
}
console.log(`a=${a},b=${b}`);
代码执行结果:
可以发现,外部变量a
和b
的值并没有改变。
造成这种现象的原因是,传入函数的参数是变量的副本,而不是变量本身。
参数默认值
在定义函数的时候,我们可以为传入的参数设定一个默认值,如果在调用函数的时候为提供参数,就会使用默认值代替。
举个例子:
function bless(name,senc='身体健康'){console.log(`祝${name},${senc}.`);
}bless('特朗普');
代码执行结果:
以上函数虽然需要两个参数,但是在调用的时候,传入一个参数并不影响使用,这是因为在定义函数的时候已经为senc
设定了默认值。
如果我们不为参数设定默认值,但是不传入对应参数会发生什么呢?
举个例子:
function bless(name,senc){console.log(`祝${name},${senc}.`);
}bless('特朗普');
代码执行结果如下:
可见,在不传递参数情况下,参数是undefined
。
年长代码的默认参数
如果在老版本的JavaScript
中如何使用参数默认值呢?
有两种方式:
- 使用
if
判断:
function doSomething(val){if(val === undefined){val = 'default val';}... ...
}
- 使用
||
运算符
function doSomething(val){val = val || 'default val';... ...
}
空值合并运算符的应用
即使在现代的JavaScript
中,同样有在函数内部判断是否传入参数的必要,除了上述两种常用于旧代码的方式外,我们还可以使用空值合并运算符:??
。
举个例子:
function doSomething(val){val = val ?? 'unknown';... ...
}
返回值
参数是一个函数的输入,而返回值则是一个函数的输出。
返回值需要使用return
关键字,将函数的计算结果返回到函数体外。
最常见的返回值例子莫过于计算两个数字的和:
let a = 1;
let b = 2;
function add(a,b){return a + b;
}let res = add(a,b);
代码执行结果:
以上代码创建了一个函数,用于加和两个变量,然后将结果返回。
在调用函数add
时,通过将返回值赋予变量res
,从而获得返回结果。
我们也可以返回一个空值(什么都不返回):
function doSomething(){console.log('return nothing');return ;//什么都不返回,程序立即结束console.log('after return');
}doSomething();
代码执行结果如下:
return
会使程序立即退出,后面的代码不再执行。
一个函数还可以拥有多个返回值:
function mulReturn(score){if(score >= 60){return '及格';}else{return '不及格';}
}
console.log(mulReturn(30));
代码执行结果:
虽然有多个return
,但是一次执行只会选择一个。
如果函数什么也不返回
return ;
,或者没有return
语句,那么它的返回值就是undefined
return陷阱
当返回表达式比较长时,我们很有可能会将其放在单独一行,如下所示:
return(a + b + c + or + c * f(d) + f(e));
绝不可以这样,因为JavaScript
的分号自动补全机制会在return
后添加;
,从而导致函数永远只会返回undefined
。
如果我们需要处理较长的返回值表达式,应该怎么做呢?
最好的方法就是使用括号:
return (a + b + c+ d + e + f
);
然后程序就永远不会出现未知的错误了~~
小技巧
- 函数通常都是一个行为,因此在命名的时候可以使用“动词+名词”的方式,再结合驼峰式命名法,可以得到一个简洁明了的函数名称,例如:
getAge();
showMsg();
createForm();
checkInput();
简化函数功能,一个函数只做一件事,例如:
add(a,b)
函数实现两个数字相加,不应该有例如alert()
的功能;checkInput()
函数应该检测输入合法性,而不应该打印valid invalid
等信息。
过于简短的函数名,会让人不知所云例如:
function a(){...}
function b(){...}
但是
JQuery
中的$
不属于此类范畴。
我们应该写出自注释的函数/代码,让代码本身简单、已读。
16.JavaScript函数、return陷阱、函数定义、参数传递、默认参数、局部变量、全局变量、返回值、技巧相关推荐
- 函数的使用(定义)(无参无返回值)
方法的使用分两步: 第一步,定义方法: 例如:下面代码定义了一个方法名为 helloEducoder ,没有参数,且没有返回值的方法,执行的操作为输出 welcome to educoder. 注意哦 ...
- 【C 语言】字符串模型 ( strstr-while 模型 | 抽象函数模型 | 业务子函数接口定义要点 | 形参指针间接赋值 | 返回值状态 | 形参指针处理 | 形参指针判空 | 形参返回值 )
文章目录 前言 一.业务子函数接口定义要点 二.完整代码示例 前言 字符串开发模型 : strstr-while/do-while 模型 : 在 字符串 中 查找 子串特征 ; 两头堵模型 : 两个指 ...
- python函数定义参数类型和返回值类型
python中我们也可以定义函数的参数类型和返回值类型,如下代码 #函数参数和返回值的类型声明,python函数类型的声明,更加有意义,更加实用一些 def add(a,b):''':param a: ...
- 如何定义带有可选参数的函数python_Python如何定义有默认参数的函数
问题 你想定义一个函数或者方法,它的一个或多个参数是可选的并且有一个默认值. 解决方案 定义一个有可选参数的函数是非常简单的,直接在函数定义中给参数指定一个默认值,并放到参数列表最后就行了.例如: d ...
- 实现 fizzBuzz 函数,参数 Thum 与返回值的关系如下: 1、如果 Thum 能同时被 3 和 5 整除,返回字符串 fizzbuzz 2、如果 Thum 能被 3 整除,返回字符串 fiz
题目描述 实现 fizzBuzz 函数,参数 Thum 与返回值的关系如下: 1.如果 Thum 能同时被 3 和 5 整除,返回字符串 fizzbuzz 2.如果 Thum 能被 3 整除,返回字符 ...
- 【python入门篇——16】Python函数详解(函数定义,参数种类、返回值、作用域等)
一 函数 定义: 函数是指将一组语句的集合通过一个名字(函数名)封装起来,要想执行这个函数,只需调用其函数名即可 特性: 1.代码重用2.保持一致性3.可扩展性 二 函数的创建 2.1 格式: Pyt ...
- Python实战从入门到精通第十四讲——定义有默认参数的函数
定义一个函数或者方法,它的一个或多个参数是可选的并且有一个默认值. 定义一个有可选参数的函数是非常简单的,直接在函数定义中给参数指定一个默认值,并放到参数列表最后就行了.例如: def spam(a, ...
- 拷贝构造,深度拷贝,关于delete和default相关的操作,explicit,类赋初值,构造函数和析构函数,成员函数和内联函数,关于内存存储,默认参数,静态函数和普通函数,const函数,友元
1.拷贝构造 //拷贝构造的规则,有两种方式实现初始化. //1.一个是通过在后面:a(x),b(y)的方式实现初始化. //2.第二种初始化的方式是直接在构造方法里面实现初始化. 案例如下: ...
- python带参数装饰器 函数名_python 全栈开发,Day11(函数名应用,闭包,装饰器初识,带参数以及带返回值的装饰器)...
一.函数名应用 函数名是什么?函数名是函数的名字,本质:变量,特殊的变量. 函数名(),执行此函数. python 规范写法 1. #后面加一个空格,再写内容,就没有波浪线了. 2.一行代码写完,下面 ...
- const参数,const返回值与const函数
在C++程序中,经常用const 来限制对一个对象的操作,例如,将一个变量定义为const 的: const int n=3; 则这个变量的值不能被修改,即不能对变量赋值. const 这个关键字 ...
最新文章
- 警惕!Cisco产品的假冒和水货
- Beamer 目录分栏
- artTemplate使用
- git统计每个人的代码行数_项目出了bug如何甩锅?使用这个Git工具帮你找到元凶...
- role cache - set data user parameter - /UI2/CACHE_DISABLE
- 少年班招生大扩容,清华、北大加入争夺行列,每年增至近800人
- oracle 列级外键,Oracle外键列上是否需要索引?
- 数据科学家最常用的十种算法和方法
- 2020-06-05 原始套接字/AF_PACKET链路层访问
- python命令行参数 空格_Python 命令行参数
- MEncoder的基础用法—6.10. 保持视频画面比例
- 云计算需要python吗_云计算开发学习笔记:Python的环境搭建
- 黑马程序员, html css javascript 前端笔记 pink老师教程
- mysql 联合主键自增_mysql auto_increment 与 联合主键冲突问题
- 2019年8月21日 星期三(韩天峰的个人简历)
- 第八章 高级搜索树 (b4)B-树: 插入
- 进程文件ntvdm.exe
- Apache IoTDB 鼠年总结
- 词法分析扫描器的设计实现
- CPC操作的万能流程方法
热门文章
- vue 绑定 keyup.enter 绑定回车键盘事件 enter键防止页面刷新
- the default discovery settings are unsuitable for production use; at least one of [discovery.seed_ho
- abc D - Polynomial division
- IO流之 File 类和字节流
- CSR8675 BLE操作经验
- 2018年固态硬盘会大规模降价吗?
- uniapp、hbuilderx做微信小程序,获取当前城市定位(省份国家街道等)
- **servlet生命周期**
- idea 解决 右边没有gradle 工具栏
- Mars3D(含Cesium)数据及服务篇:TIF地形转terrain格式