整合营销服务商

电脑端+手机端+微信端=数据同步管理

免费咨询热线:

JavaScript中的函数及argument应用

JavaScript中的函数及argument应用



喽大家好,我是作者“未来”,本期分享的内容是Web前端系列课程,本系列总共29个阶段,坚持学习3个月蜕变为Web前端高手哦!

志同道合的小伙伴跟我一起学习交流哦!


第三阶段 JavaScript基础


15 函数

把一段相对独立的具有特定功能的代码块封装起来,形成一个独立实体,就是函数,起个名字(函数名),在后续开发中可以反复调用。

函数的作用就是封装一段代码,将来可以重复使用。

例:通过函数求两个数字的和。


函数的定义

特点:

函数声明的时候,函数体并不会执行,只有当函数被调用的时候才会执行。

函数一般都用来干一件事情,需用使用动词+名词,表示做一件事情 `tellStory` `sayHello`等。

注意:

函数需要先定义,然后才能使用

函数名字:要遵循驼峰命名法。

函数一旦重名,后面的会把前面的函数覆盖。

Ctrl +鼠标左键---->转到定义。

一个函数最好就是一个功能。


函数的调用

调用函数的语法:

函数名();

特点:

函数体只有在调用的时候才会执行,调用需要()进行调用。

可以调用多次(重复使用)。

代码示例:


函数的参数

在函数定义的时候,函数名字后面的小括号里的变量就是参数,目的是函数在调用的时候,对用户传进来的值操作。


形参:函数在定义的时候小括号里的变量叫形参。

实参:函数在调用的时候小括号里传入的值叫实参,实参可以是变量也可以是值。

函数内部是一个封闭的环境,可以通过参数的方式,把外部的值传递给函数内部。

调用的时候,把实参1的值给形参1,把实参2的值给形参2……


函数的返回值

当函数执行完的时候,并不是所有时候都要把结果打印。我们期望函数给我一些反馈(比如计算的结果返回进行后续的运算),这个时候可以让函数返回一些东西。也就是返回值。函数通过return返回一个返回值。

在函数内部有return关键字,并且在关键字后面有内容,这个内容被返回了。

当函数调用之后,需要这个返回值,那么就定义变量接收即可。

返回值语法:

函数的调用结果就是返回值,因此我们可以直接对函数调用结果进行操作。


返回值详解:

-如果一个函数中有return ,那么这个函数就有返回值。

-如果一个函数中没有return,那么这个函数就没有返回值。

-如果一个函数中没有明确的返回值,那么调用的时候接收了,结果就是undefined

(没有明确返回值:函数中没有return,函数中有return,但是return后面没有任何内容)。

-函数没有返回值,但是在调用的时候接收了,那么结果就是undefined。

-变量声明了,没有赋值,结果也是undefined。

-如果一个函数有参数,有参数的函数。

-如果一个函数没有参数,没有参数的函数。

-形参的个数和实参的个数可以不一致。

-return 下面的代码是不会执行的。


案例

- 求1-100之间所有数的和

-求1-n之间所有的数字的和

- 求n-m之间所有数的和

- 圆的面积

-求三个数中的最大数

-判断一个数是不是素数

-求两个数字的差

-求一组数字中的最大值

-求一个数组中的最大值和最小值还有和

-通过函数实现数组反转

-通过函数实现冒泡排序

- 求阶乘


arguments的使用

定义一个函数,如果不确定用户是否传入了参数,或者说不知道用户传了几个参数,没办法计算,可以使用arguments。

JavaScript中,arguments对象是比较特别的一个对象,实际上是当前函数的一个内置属性。也就是说所有函数都内置了一个arguments对象,arguments对象中存储了传递的所有的实参。arguments是一个伪数组,因此可以进行遍历。


案例

求任意个数的和

?

看不懂的小伙伴不要气馁,后续的分享中将持续解释,只要你跟着我分享的课程从头到尾去学习,每篇文章看三遍,一个月后,回过头来看之前的文章就会感觉简单极了。

本章已结束,下篇文章将分享《函数其它补充,作用域、预解析》小伙伴们不要错过哟!

这里是云端源想IT,帮你轻松学IT”

嗨~ 今天的你过得还好吗?

不必让种种记忆永远和自己同在

就让它留在它所形成的地方吧

- 2024.05.13 -


JavaScript是一种基于原型的高级、解释型编程语言,它是一门动态语言,常用于网页交互和前后端开发。在JavaScript中,函数是一段可重复使用的代码块,它可以执行一个特定的任务。

函数的使用可以增加代码的模块性和重用性,使得代码更加简洁明了。本文将介绍如何在JavaScript中创建和使用函数。



一、函数的介绍

简单来说,函数就是一段可重复使用的代码块,它可以接收输入参数,执行特定的操作,并返回结果。在JavaScript中,我们可以使用关键字function来定义一个函数。例如:

function add(a, b) {
return a + b;
}

这个简单的函数接受两个参数a和b,然后返回它们的和。


函数的作用:

  • 实现功能的封装,提高代码复用率
  • 用于构建对象的模板(构造函数)

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


二、函数的创建

在JavaScript中,有多种方式可以用来创建函数,其中最常用的有以下几种:


1、函数声明(Function Declaration)

函数声明是最常见的创建函数的方式,它使用function关键字,后跟函数名和参数列表,然后是函数体。

例如,我们可以创建一个名为greet的函数,该函数接收一个参数name,并打印出一条问候消息:

function greet(name) {
console.log("Hello, " + name + "!");
}


2、函数表达式(Function Expression)

函数表达式是将函数定义为一个表达式的值。它与函数声明类似,但是没有函数名。


例如,我们可以创建一个匿名函数,并将其赋值给一个变量greet:

var greet=function(name) {
console.log("Hello, " + name + "!");
};

3、箭头函数(Arrow Function)

箭头函数是ES6引入的新特性,它提供了一种更简洁的方式来创建函数。箭头函数使用=>符号,左侧是参数列表,右侧是函数体。


例如,我们可以创建一个箭头函数,并将其赋值给一个变量greet:

var greet=(name)=> {
console.log("Hello, " + name + "!");
};


三、函数内部属性

函数内部属性只能在函数内部才能访问。

arguments

arguments是一个类数组对象,包含着传入函数中的所有参数。arguments主要用途是保存函数参数。

function foo(){
console.log(arguments) // [Arguments] { '0': 1, '1': 2, '2': 3, '3': 4 }
console.log(arguments[1]) // 2
}
// 当传递的实参个数超过形参的个数的时候不会报错,所有的实参都会保存在arguments里
foo(1,2,3,4)



注意:arguments 中存的是实参,而不会存形参。

function foo(a,b=2,c=3){
console.log(arguments) // [Arguments] { '0': 1 }
console.log(b) //2
console.log(c) //3
}
//只传了一个实参,那么arguments中就只有一个值
foo(1)


callee 属性

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

arguments.callee 实际上就是函数名。
// 递归求n的阶乘
function factorial(n) {
if (n==1) {
return 1
}
return arguments.callee(n - 1) * n //arguments.callee 相当于函数名factorial
}
console.log(factorial(10));


length 属性

arguments 对象的 length 属性返回实参个数。
function foo(){
console.log(arguments.length) //5
}
foo(1,2,3,4,5)


四、函数的使用

创建了函数后,我们就可以在代码中调用它来执行特定的任务。函数调用是通过函数名和括号内的参数列表来实现的。


例如,我们可以调用上面创建的greet函数:

greet("Alice"); // 输出:Hello, Alice!

此外,JavaScript还支持以下高级功能:


1、默认参数:

可以为函数的参数设置默认值,当调用函数时未提供该参数时,将使用默认值。

function greet(name="World") {
console.log("Hello, " + name + "!");
}

greet(); // 输出:Hello, World!
greet("Alice"); // 输出:Hello, Alice!



2、回调函数:

可以将函数作为参数传递给其他函数,以便在特定时机执行

setTimeout(function() {
console.log("This message will be displayed after 1 second.");
}, 1000);


3、递归函数:

函数可以直接或间接地调用自身,以实现复杂的逻辑。

function factorial(n) {
if (n===0) {
return 1;
} else {
return n * factorial(n - 1);
}
}

console.log(factorial(5)); // 输出:120


五、函数的作用域

JavaScript函数的作用域分为全局作用域和局部作用域。


全局作用域:全局作用域中的变量是在任何函数之外声明的,或者是使用var关键字在一个函数内部声明但没有使用let或const的变量。这些变量在整个程序中都是可用的。


局部作用域:局部作用域中的变量是在函数体内声明的,包括使用let、const或var关键字声明的变量。这些变量只在函数内部及其子函数中可用,函数外部无法访问。


此外,JavaScript还有块级作用域,由{}包围的代码块也可以创建新的作用域,通常用于控制流语句(如if、for等)中。在块级作用域中声明的变量,在块外部是不可见的。


六、什么是闭包

1、什么是闭包

简单讲,闭包就是指有权访问另一个函数作用域中的变量的函数。


闭包是一种特殊的对象。它由两部分构成:函数以及创建该函数的环境。环境由闭包创建时在作用域中的任何局部变量组成。


2、闭包形成的条件

闭包的生成有三个必要条件:

  • 函数嵌套函数
  • 内部函数引用了外部函数中的数据(属性、函数)
  • 参数和变量不会被回收

这样就形成了一个不会销毁的函数空间。

下面例子中的 closure 就是一个闭包:

function func() {
var a=1, b=2;

function closure() {
return a + b;
}
return closure;
}
console.log(func()()); // 3


闭包的作用域链包含着它自己的作用域,以及包含它的函数的作用域和全局作用域。



在Javascript语言中,只有函数内部的子函数才能读取局部变量,因此可以把闭包简单理解成 " 定义在一个函数内部的函数 " 。


所以,在本质上,闭包就是将函数内部和函数外部连接起来的一座桥梁。


3、闭包的作用

闭包可以用在许多地方。它的最大用处有两个,一个是可以读取函数内部的变量,另一个就是让这些变量的值始终保持在内存中

function f1() {
var n=999;
nAdd=function () {
n +=1
}
function f2() {
console.log(n);
}
return f2;
}
var result=f1();
result(); // 999
nAdd();
result(); // 1000


在这段代码中,result 实际上就是闭包 f2函数。它一共运行了两次,第一次的值是999,第二次的值是1000。这证明了,函数f1中的局部变量n一直保存在内存中,并没有在f1调用后被自动清除。


为什么会这样呢?原因就在于f1是f2的父函数,而f2被赋给了一个全局变量,这导致f2始终在内存中,而f2的存在依赖于f1,因此f1也始终在内存中,不会在调用结束后,被垃圾回收机制(garbage collection)回收。



这段代码中另一个值得注意的地方,就是"nAdd=function(){n+=1}"这一行,首先在nAdd前面没有使用var关键字,因此nAdd是一个全局变量,而不是局部变量。


其次,nAdd的值是一个匿名函数(anonymous function),而这个匿名函数本身也是一个闭包,所以nAdd相当于是一个setter,可以在函数外部对函数内部的局部变量进行操作。


4、使用闭包的注意点


(1)由于闭包会使得函数中的变量都被保存在内存中,内存消耗很大,所以不能滥用闭包,否则会造成网页的性能问题,在IE中可能导致内存泄露,这是IE的BUG。解决方法是,在退出函数之前,将不使用的局部变量全部删除。


(2)闭包会在父函数外部改变父函数内部变量的值。所以,如果你把父函数当作对象(object)使用,把闭包当作它的公用方法(Public Method),把内部变量当作它的私有属性(private value),这时一定要小心,不要随便改变父函数内部变量的值。

多个子函数的scope都是同时指向父级,是完全共享的。因此当父级的变量对象被修改时,所有子函数都受到影响。


JavaScript函数的创建和使用是编程过程中的基本技能,掌握好函数的使用可以使代码更加模块化、简洁和高效。它们不仅可以帮助我们将代码模块化、复用,还可以实现更复杂的逻辑和功能。

希望这篇文章能帮助你更好地理解和应用JavaScript函数,让你的编程之旅更加精彩!



我们下期再见!


END

文案编辑|云端学长

文案配图|云端学长

内容由:云端源想分享

数(Function)是被设计为执行特定任务的代码块。它在可以实现定制运算功能的同时,还带有一个入口和一个出口。所谓的入口,就是函数所带的各个参数,我们可以通过这个入口,把函数的参数值代入子程序,供计算机处理;所谓出口,就是指函数的函数值,在计算求得结果之后,由此口带回给调用它的程序。

在程序设计中,常将一些常用的功能模块编写成函数,放在函数库中供用户选用。善于利用函数,可以减少重复编写程序段的工作量。

本文介绍Javascript函数的几种常用定义方式。掌握JS函数基本技术后,在统计数据处理过程中,我们将函数理解为某一统计对象(项目)所定制的方法。

导读:

  • 普通函数
  • 函数arguments对象
  • 匿名函数
  • 闭包和递归函数
  • Promise回调函数

1、普通函数

I、基本语法

function 函数名称(参数1, 参数2, 参数3) {
		//要执行的代码
return 返回值
}

JavaScript函数语法解析如下:

  • JavaScript函数通过function关键词进行定义,其后是函数名称和括号()
  • 函数名可包含字母、数字、下划线和美元符号
  • 圆括号可包括由逗号分隔的参数
  • 由函数执行的代码被放置在花括号{}中
  • 函数返回值由return关键字指定

II、无参数函数

console.clear();
function test1() {
return "Hello World!";
}
//执行函数返回"Hello World!",并赋值给变量str
var str=test1();
console.log(str);

注:Console对象用于JavaScript调试,为了显示Console.log输出结果,通过按Control+Shift+i(PC平台)来打开Console窗口

III、有参数函数

//计算任意两个数的和
function oSum(x, y) {
return x+y;
}
var mySum=oSum(15, 85);
console.log(mySum); //100

IV、参数默认值设置

//求和函数中给两个参数设置默认值
console.clear();
function oSum(x=50, y=50) {
return x+y;
}
var mySum=oSum(15, 55);
console.log(mySum); //70
mySum=oSum(15);
console.log(mySum); //65
mySum=oSum();
console.log(mySum); //100

V、参数为函数

console.clear();
function oSum(x, y) {return x+y;}
var mySum=oSum(oSum(45, 75), 100);
console.log(mySum); //220

VI、对象{}为参数 - 解构赋值默认值

console.clear();
function oSum({x=10, y=20}) {
return x+y;
}
console.log(oSum({})); //30,这里直接调用oSum()出错
console.log(oSum({x:100})); //120
console.log(oSum({y:100})); //110
console.log(oSum({x:100,y:200})); //300
console.log(oSum({y:50,x:20})); //70

VII、对象{}为参数 - 双重默认值

//代码容错更好
console.clear();
function oSum({x=10, y=20}={}) {
return x+y;
}
console.log(oSum()); //30
console.log(oSum({})); //30
console.log(oSum({x:100})); //120
console.log(oSum({y:100})); //110
console.log(oSum({x:100,y:200})); //300
console.log(oSum({y:50,x:20})); //70

2、函数arguments对象

在JavaScript中,参数在函数内部是以一个数组表示的,arguments是函数内部的一个专门用来存储实参的数组对象。函数arguments的对象在函数运行时用于检测和重新设置参数。

I、arguments.length - 函数参数数量

console.clear();
function fn(a,b,c){
console.log(arguments.length); //3
return a+b+c;
}
console.log(fn(1,2,3)); //6

II、arguments[] - 函数输出和设置

console.clear();
function fn(a,b,c){
console.log(arguments[0]); //1
console.log(arguments[1]); //2
console.log(arguments[2]); //3
arguments[0]=5; //重新设置参数a=5
return a+b+c;
}
console.log(fn(1,2,3)); //10

III、arguments转数组

arguments对象不是一个真正的数组 ,它类似于数组,但除了length属性和索引元素之外没有任何数组属性。例如,它没有pop方法。但是它可以被转换为一个真正的数组,转换为真实的数组后就可以使用完整的数组方法

console.clear();
function fn(a, b, c) {
var arr=Array.from(arguments); //进行转数组操作
console.log(arr); //输出数组
return a + b + c;
}
console.log(fn(1, 2, 3)); //6

3、匿名函数

匿名函数顾名思义指的是没有名称的函数,在实际开发中使用的频率非常高,是学好JS编程的重点。

I、变量匿名函数

console.clear();
var fn=function fn(a,b,c=9) {
return a+b+c;
}
console.log(fn(1,2)); //12
console.log(fn(1,2,3)); //6

II、无名称匿名函数

即在函数声明时,在后面紧跟参数。JS语法解析此函数时,里面代码立即执行。

console.clear();
console.log(function(a,b){return a+b;}(2,3));
console.clear();
//加括号执行无匿名函数(输出"Hello Word!")
(function (){
		console.log("Hello Word!");
})()
//加括号执行有匿名函数(输出"Hello Word! lei.")
(function (str){
		console.log("Hello Word!" +" "+ str +".");
})("lei")

注:函数代码function(a,b){return a+b;}没指定函数名称,如果需要执行匿名函数,在匿名函数后面加上一个括号即可立即执行

III、事件绑定匿名函数

通常我们浏览网页时会通过鼠标或键盘输入信息,例如鼠标点击某个按钮称“click点击事件”、文本框内文字信息改变了称“change事件”。总之,用户所有的鼠标、键盘操作都称为事件,都可以通过JS代码来捕获这些事件。

console.clear();
//通过id或取图标对象
var logo=document.querySelector("#myLogo");
//给左上角“银河统计”图标增加点击事件
logo.onclick=function(){
		console.log("欢迎来到银河统计工作室!");
}
logo.onmousemove=function(){
    logo.style.cursor="pointer";
    console.log("鼠标在图像上面!");
}
logo.onmouseout=function(){
    logo.style.cursor="default";
    console.log("鼠标已经离开图像!");
}

注:代码中网页图像标记为<img id="myLogo" src="###"/>

IV、对象绑定匿名函数做为对象的方法

前面我们介绍JS对象时提到,事件是有属性和方法组成的数据结构,事件的方法可以通过绑定匿名函数的方式建立。

console.clear();
    var obj={
    name:"Carolyn",
    age:11,
    fn:function(str){
    		return "My name is "+this.name+" Siyu"+". I'm "+this.age+" years old now.";
    }
};
console.log(obj.fn("Siyu")); //My name is Carolyn Siyu. I'm 11 years old now.

注:这里定匿名函数为属性的返回值

V、匿名函数做为回调函数(callback)

什么是同步,什么是异步?

同步指的是一次只能完成一件任务。如果有多个任务,就必须排队,前面一个任务完成,再执行后面一个任务,以此类推。

异步指的是每一个任务有一个或多个回调函数(callback),前一个任务结束后,不是执行后一个任务,而是执行回调函数,后一个任务则是不等前一个任务结束就执行,所以程序的执行顺序与任务的排列顺序是不一致的、异步的。

JS是单线程的,它本身不可能是异步的,通过回调函数可以实现异步。JS中最基础的异步是setTimeout和setInterval函数。

console.clear();
var interval=setInterval(function(){
		console.log("回调函数,每间隔1秒钟会被执行一次");
},1000);
//点击银河统计图表停止setInterval计算器运行
var logo=document.querySelector("#myLogo");
logo.onclick=function(){
    console.log("Stop!");
    clearInterval(interval)
}
setTimeout(function() {
		console.log("张三")
}, 1000 );
setTimeout(function() {
		console.log("李四")
}, 2000 );
setTimeout(function() {
		console.log("王五")
}, 3000 );
//jS最基础的异步实现
function a() {
    console.log("执行a函数");
    setTimeout(function() {
    		console.log("执行a函数的延迟函数");
    },2000);
}
function b() {
		console.log("执行b函数");
}
a();
b();

VI、匿名函数做为返回值

console.clear();
function fn(){
    return function(){
    		return "Carolin";
    }
}
//调用匿名函数
console.log(fn()()); //Carolin
//或者
var box=fn();
console.log(box()); //Carolin

4、闭包和递归函数

假设,函数A内部声明了个函数B,函数B引用了函数B之外的变量,并且函数A的返回值为函数B的引用,那么函数B就是闭包函数。

递归就是函数自己调用自己,当函数自己时,其自身为闭包函数,参数为域外变量。

console.clear();
function funA(arg1,arg2) {
    var i=0; //funA作用域的变量
    function funB(step) {
        i=i + step; //访问funB作用域外变量i
        console.log(i)
    }
    return funB;
}
var allShowA=funA(2, 3); //调用的是funA arg1=2,arg2=3
allShowA(1);//调用的是funB step=1,输出 1
allShowA(3);//调用的是funB setp=3,输出 4
//累加
console.clear();
function f(num){
    if(num<1) {
   		 return 0;
    } else {
    		return f(num-1)+num;
    }
}
console.log(f(9)); //45
//阶乘
console.clear();
function f(num){
    if(num<1) {
    return 1;
    } else {
    return f(num-1)*num;
    }
}
console.log(f(4)); //24
//在对象中定义递归方法
var obj={
    num : 5,
    fac : function (x) {
        if (x===1) {
        		return 1;
        } else {
        		return x * obj.fac(x - 1);
        }
    }
};
console.log(obj.fac(5)) /120
//使用arguments.callee
function fact(num){
    if (num<=1){
    		return 1;
    }else{
   		 return num*arguments.callee(num-1);
    }
}
console.log(fact(4)); //24

5、Promise回调函数

Promise是ES6语言标准中提供的对象。Promise是异步编程的一种解决方案,比传统的解决方案(回调函数和事件)更合理和更强大。

console.clear();
//基本用法,
var p=new Promise(function(resolve, reject){
    setTimeout(function(){
    		resolve(console.log("done"));
    }, 1000);
});
//做为对象返回
function timeout(ms) {
    return new Promise((resolve, reject)=> {
    		setTimeout(resolve, ms, 'done');
    });
}
timeout(1000).then((value)=> { //参数value='done'
		console.log(value);
});
//完整使用方法
function promiseTest(){
let p=new Promise(function(resolve, reject){
    setTimeout(function(){
        var num=Math.random()*100; //生成1-100的随机数
        console.log('随机数生成的值:',num)
        if(num>=60){
            resolve(num);
        } else {
            reject('数字太于60了即将执行失败回调');
        }
        }, 2000);
    })
    return p
}
promiseTest().then(
    function(data){ //data=num
        console.log('resolved成功回调');
        console.log('成功回调接受的值:',data);
    }
)
.catch(function(reason, data){
    console.log('catch到rejected失败回调');
    console.log('catch失败执行回调抛出失败原因:',reason);
});

注:Promise回调函数在网页数据抓取时常常遇到

JavaScript是一种面向对象的编程语言,因此对象在JavaScript中扮演了很重要的角色。

Javascript函数是能完成某个常用功能的一小段代码,而Javascript方法(method)是通过对象调用的Javascript函数。

JS中所有事物都是对象,对象是拥有属性和方法的数据。但是,JS对象又是由函数创建的,JS函数本身也是对象。“方法是函数、对象是函数”,JS中函数的用途和含义有点绕口,需要大量练习和运用才能掌握。