【js面试题】JavaScript 中箭头函数与普通函数的深度剖析

在 JavaScript 编程的世界里,函数是极为重要的组成部分。而随着 ES6 的出现,箭头函数成为了 JavaScript 函数家族中的新成员。它与传统的普通函数有着诸多的不同之处,这些差异深刻地影响着我们编写代码的方式以及代码的执行逻辑。本文将对 JavaScript 中的箭头函数与普通函数进行全面而深入的剖析,帮助大家更好地理解和运用这两种函数类型。

一、语法结构对比

(一)普通函数的语法

普通函数的定义使用 function 关键字,其基本语法结构如下:

function functionName(parameters) {// 函数体return value;
}
function add(a, b) {return a + b;
}

这里 function 关键字明确标识了这是一个函数定义,add 是函数名,(a, b) 是参数列表,花括号内的部分是函数体,通过 return 语句返回函数的计算结果。

(二)箭头函数的语法

箭头函数则采用了更为简洁的箭头 => 语法。如果函数体只有一行且是返回值表达式,那么可以省略花括号和 return 关键字,其语法形式为:

(parameters) => expressionconst add = (a, b) => a + b;

在这个例子中,(a, b) 是参数列表,=> 后面直接跟着返回值表达式 a + b。如果函数体有多行代码,则需要使用花括号包裹,并显式使用 return 关键字(如果有返回值),语法如下:

(parameters) => {// 多行函数体return value;
}
const multiplyAndLog = (a, b) => {const result = a * b;console.log(result);return result;
}

二、this 指向的差异

(一)普通函数的 this 指向

普通函数的 this 指向在函数被调用时确定,它取决于函数的调用方式。在全局环境下直接调用函数时,非严格模式下 this 指向全局对象(在浏览器中是 window),严格模式下 this 为 undefined。例如:

function globalFunction() {console.log(this);
}
globalFunction(); // 在非严格模式下输出 windowfunction strictFunction() {'use strict';console.log(this);
}
strictFunction(); // 输出 undefined

当函数作为对象的方法被调用时,this 指向该对象。例如:

const myObject = {name: 'Object',myMethod: function() {console.log(this.name);}
};
myObject.myMethod(); // 输出 'Object'

如果函数被作为构造函数使用,通过 new 关键字创建对象实例,那么 this 指向新创建的对象实例。例如:

function Person(name) {this.name = name;this.sayHello = function() {console.log('Hello, my name is'+ this.name);};
}
const person = new Person('John');
person.sayHello(); // 输出 'Hello, my name is John'

(二)箭头函数的 this 指向
箭头函数没有自己的 this,它的 this 是在定义时继承自外层作用域的 this。例如:

const outerObject = {name: 'Outer',regularFunction: function() {const arrowFunction = () => {console.log(this.name);};arrowFunction();}
};
outerObject.regularFunction(); // 输出 'Outer'

在这个例子中,箭头函数 arrowFunction 内部的 this 继承自外层函数 regularFunction 的 this,也就是 outerObject。无论箭头函数在何处被调用,其 this 始终保持与定义时外层作用域的 this 一致。这种特性使得在处理回调函数等场景中,箭头函数能够避免 this 指向的混淆。例如:

const button = document.getElementById('myButton');
button.addEventListener('click', function() {// 这里的 this 指向 button 元素console.log(this);const innerArrowFunction = () => {// 箭头函数的 this 继承自外层函数,也就是 button 元素console.log(this);};innerArrowFunction();
});

三、arguments 对象的使用

(一)普通函数的 arguments

普通函数内部有一个内置的 arguments 对象,它包含了函数被调用时传入的所有参数。例如:

function sumAll() {let sum = 0;for (let i = 0; i < arguments.length; i++) {sum += arguments[i];}return sum;
}
console.log(sumAll(1, 2, 3, 4)); // 输出 10

这里 arguments 可以获取到传入的所有参数值,即使函数定义时没有指定具体的参数名。
(二)箭头函数与 arguments

箭头函数没有自己的 arguments 对象。如果在箭头函数中需要访问参数列表,可以使用剩余参数语法(…)。例如:

const sumAllArrow = (...args) => {let sum = 0;for (let i = 0; i < args.length; i++) {sum += args[i];}return sum;
}
console.log(sumAllArrow(1, 2, 3, 4)); // 输出 10

四、构造函数的适用性

(一)普通函数作为构造函数

普通函数可以通过 new 关键字作为构造函数来创建对象实例。在构造函数内部,this 指向新创建的对象实例,可以用来初始化对象的属性和方法。例如:

function Person(name) {this.name = name;this.sayHello = function() {console.log('Hello, my name is'+ this.name);};
}
const person = new Person('John');
person.sayHello(); // 输出 'Hello, my name is John'

(二)箭头函数不能作为构造函数
箭头函数不能被用作构造函数,因为它没有自己的 this,无法进行对象实例的初始化操作。如果尝试使用 new 关键字调用箭头函数,会抛出错误。例如:

const ArrowPerson = (name) => {this.name = name;this.sayHello = () => {console.log('Hello, my name is'+ this.name);};
}
const arrowPerson = new ArrowPerson('Alice'); // 抛出错误

总结

在 JavaScript 中,箭头函数和普通函数在语法结构、this 指向、arguments 对象使用以及构造函数适用性等方面都存在明显的差异。 普通函数具有较为复杂的 this 指向规则,其在不同的调用方式下 this 会指向不同的对象,同时拥有内置的 arguments 对象方便获取所有传入参数,并且可以作为构造函数创建对象实例。而箭头函数以简洁的语法著称,其 this 指向在定义时确定并继承自外层作用域,没有自己的 arguments 对象,不能作为构造函数使用。在实际编程中,我们需要根据具体的需求和场景来选择使用箭头函数还是普通函数。如果需要动态确定 this 指向、使用 arguments 对象或者创建对象实例,那么普通函数是合适的选择;而如果希望保持 this 与外层作用域一致,且函数逻辑较为简单,箭头函数则能提供更简洁清晰的代码表达方式。深入理解这两种函数的特性,有助于我们编写更加高效、可读和可维护的 JavaScript 代码,提升我们的编程能力和代码质量。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.xdnf.cn/news/36006.html

如若内容造成侵权/违法违规/事实不符,请联系一条长河网进行投诉反馈,一经查实,立即删除!

相关文章

【漫话机器学习系列】Adaboost算法

Adaboost&#xff08;Adaptive Boosting&#xff09;是一种经典的集成学习方法&#xff0c;主要思想是通过将多个弱学习器&#xff08;通常是简单模型&#xff0c;如决策树桩&#xff09;加权组合&#xff0c;来提升整体模型的预测能力。Adaboost 是一种自适应的学习方法&#…

SQL靶场第四关

sql靶场第四关攻略 输入?id1页面正常 输入?id1发现页面也正常 输入?id1"&#xff0c;页面异常&#xff0c;说明存在sql报错注入 在输入?id1" --页面还是报错 1.判断闭合点 我们需要找到闭合点&#xff0c;尝试在双引号后面加个) 输入?id1") --我们发现…

Trunk链路操作题

Trunk链路操作题 论证&#xff1a;

Alogrithm:三色棋

1. 说明 三色旗的问题最早由 E.W.Diikstra 所提出&#xff0c;他所使用的用语为 Dutch Nation Flag&#xff08;Dijkstra 为荷兰人&#xff09;&#xff0c;而多数的作者则使用 Three-Color Flag 来称之。 假设有一条绳子&#xff0c;上面有红、白、蓝三种颜色的旗子&#xff0…

需要排序的子数组

题目描述 给定一个无序数组arr&#xff0c;求出需要排序的最短子数组长度 要求&#xff1a;O(N) 如输入&#xff1a;arr{2,3,7,5,4,6}&#xff0c;返回4&#xff0c;因为只有{7,5,4,6}需要排序。 分析 以{2,3,7,5,4,6,8,9}为例&#xff1a; 前端小于最小波谷&#xff08;3…

Python酷库之旅-第三方库Pandas(154)

目录 一、用法精讲 701、pandas.Timestamp.utcnow方法 701-1、语法 701-2、参数 701-3、功能 701-4、返回值 701-5、说明 701-6、用法 701-6-1、数据准备 701-6-2、代码示例 701-6-3、结果输出 702、pandas.Timestamp.utcoffset方法 702-1、语法 702-2、参数 70…

如何启动神通数据库?神通数据库的启动方式一共有几种?

简单总结&#xff0c;神通数据库启动有三种方式&#xff1a; 1、dba管理工具方式 2、服务方式 &#xff08;1&#xff09;service oscardb_OSRDBd restart &#xff08;2&#xff09;/etc/init.d/oscardb_OSRDBd restart &#xff08;3&#xff09;systemctl start oscardb_OS…

Modbus Poll的使用

最近从串口调试助手接触到了Modbus Poll&#xff0c;一开始用的时候有些生疏&#xff0c;了解之后不得不说真香。 相对于串口调试助手&#xff0c;有些设备厂家会给一些点表和指令码&#xff0c;有些也可以通过modbus协议解析出来&#xff0c;相对来说&#xff0c;使用Modbus …

第四学期-智能数据分析-期末复习题

智能数据分析期末复习&#xff08;2024春&#xff09; 【考试形式】&#xff1a;闭卷&#xff0c;90分钟&#xff0c;笔试 【题型分布】&#xff1a; 单选题10题&#xff0c;每题3分&#xff0c;共计30分 判断题10题&#xff0c;每题2分&#xff0c;共计20分 填空题5题&…

总结的一些MySql面试题

目录 一&#xff1a;基础篇 二&#xff1a;索引原理和SQL优化 三&#xff1a;事务原理 四&#xff1a;缓存策略 一&#xff1a;基础篇 1&#xff1a;定义&#xff1a;按照数据结构来组织、存储和管理数据的仓库&#xff1b;是一个长期存储在计算机内的、有组织的、可共享 的…

C#实现一个HttpClient集成通义千问-开发前准备

集成一个在线大模型&#xff08;如通义千问&#xff09;&#xff0c;来开发一个chat对话类型的ai应用&#xff0c;我需要先了解OpenAI的API文档&#xff0c;请求和返回的参数都是以相关接口文档的标准进行的 相关文档 OpenAI API文档 https://platform.openai.com/docs/api-…

python游戏设计---飞机大战

1.前言 上次做飞机大战游戏有人这么说&#xff1a; 好好好&#xff01;今天必须整一个&#xff0c;今天我们来详细讲解一下&#xff0c;底部找素材文件下载&#xff01;&#xff01;&#xff01; 2.游戏制作 目录如下&#xff1a; 1.导入的包 import pygame import sys imp…

Final Vision Get Picture Pos Send 2 Python Control Robot

import tkinter as tk from tkinter import messagebox, filedialog from tkinter import ttk import socket import threading import subprocess from datetime import datetime from PIL import Image, ImageTk import time # 全局变量 client_socket None connected Fal…

Spring框架-IoC的使用(基于XML和注解两种方式)

一、Spring IoC使用-基于XML 1 IoC使用-基于XML 使用SpringIoC组件创建并管理对象 1.1 创建实体类 package com.feng.ioc.bean;import java.util.Date;/*** program: spring-ioc-demo1* description: 学生实体类* author: FF* create: 2024-12-04 18:53**/ public class Stud…

C++编程控制舵机的实现与应用

在嵌入式编程和物联网应用中&#xff0c;舵机是一种非常重要的执行器&#xff0c;广泛应用于机器人、遥控玩具、机械臂、摄像头云台等多个领域。舵机不仅能够精准地控制角度位置&#xff0c;还能在一定的工作范围内持续保持该位置。在本篇文章中&#xff0c;我们将站在 C 编程教…

对于MySQL中视图的相关实验

以下用该表举例&#xff1a; /*Table structure for table employees */ DROP TABLE IF EXISTS employees; CREATE TABLE employees ( employee_id int(6) NOT NULL DEFAULT 0, first_name varchar(20) DEFAULT NULL, last_name varchar(25) NOT NULL, email varc…

day-90 使数组为空的最少操作次数

思路 统计每个数字出现的次数&#xff0c;计算每个数字的操作次数&#xff0c;将所有操作次数累加返回即可 解题过程 对于每个数字&#xff08;假设出现次数num&#xff09;,如果num等于1,返回-1&#xff1b;如果num%3等于0&#xff0c;返回num/3&#xff1b;如果num%3不等于0…

6.xftp使用教程

xftp用于windows和linux之间进行文件互传 1.先安装xftp软件&#xff0c;并双击打开 2.文件 – 新建 3.配置参数 4.连接 5.把需要的文件扯到右边

[nmap] 端口扫描工具的下载及详细安装使用过程(附有下载文件)

前言 nmap网络连接端扫描软件&#xff0c;用于主机发现、端口扫描、版本侦测、操作系统侦测 namp 链接&#xff1a;https://pan.quark.cn/s/4ea55a2d62c3 提取码&#xff1a;aXnr 下载压缩包后解压 &#xff01;&#xff01;安装路径不要有中文 链接失效&#xff08;可能被官…

详解组合模式

引言 有一种情况&#xff0c;当一组对象具有“整体—部分”关系时&#xff0c;如果我们处理其中一个对象或对象组合&#xff08;区别对待&#xff09;&#xff0c;就可能会出现牵一发而动全身的情况&#xff0c;造成代码复杂。这个时候&#xff0c;组合模式就是一种可以用一致的…