一、javascript面试必考基础知识点
在每一次 javascript面试 中,基础都是面试官首先考察的环节。以下知识点几乎出现在所有前端岗位的面试中,是每位求职者必须牢固掌握的基石。
数据类型与类型检测
JavaScript 中有 7 种基本数据类型:Number、String、Boolean、Undefined、Null、Symbol、BigInt,以及引用类型 Object。面试中常考 typeof、instanceof、Object.prototype.toString.call() 的区别与应用场景,尤其是如何准确检测 Array、Date、RegExp 等类型。
作用域与闭包
作用域链、词法作用域、执行上下文是 javascript面试 中的高频考点。闭包则是最能体现开发者对 JS 理解深度的知识点之一——包括闭包的形成原理、内存泄漏风险、实际应用场景(如函数柯里化、模块化、防抖节流)等。
this指向与调用方式
this 的指向取决于函数的调用方式:默认绑定、隐式绑定、显式绑定(call/apply/bind)、new 绑定、箭头函数继承外层 this。面试中常结合具体代码片段让候选人判断 this 的值,需要熟练掌握各类场景下的规则。
原型与原型链
每个对象都有一个 __proto__ 指向其构造函数的 prototype,prototype 上又有 constructor 指回构造函数,形成原型链。面试常考 instanceof 原理、原型继承、Object.create() 用法、以及 ES6 class 与原型的关系。
事件循环 Event Loop
理解同步任务、宏任务(setTimeout、setInterval、I/O)、微任务(Promise.then、MutationObserver、queueMicrotask)的执行顺序是 javascript面试 的必考题。需要掌握 V8 引擎的事件循环机制,能够准确预测代码输出顺序。
异步编程模式
从回调函数到 Promise 再到 async/await,异步编程经历了三次演进。面试中常考 Promise 的链式调用、Promise.all / Promise.race / Promise.allSettled 的区别、async/await 的错误处理(try-catch)、以及 Generator 函数的用法。
二、ES6+ 新特性面试题解析
随着 ECMAScript 标准的快速迭代,ES6 及后续版本的新特性已成为 javascript面试 中不可或缺的一部分。以下按重要程度梳理了最常考察的新特性。
let / const 与 var 的区别
在 javascript面试 中,变量声明方式是 ES6 最基础的考点。let 和 const 具有块级作用域,不存在变量提升(暂时性死区),而 var 具有函数作用域且存在变量提升。const 声明常量,一旦赋值不可重新赋值(但引用类型内部属性可修改)。
var a = 1;
let b = 2;
const c = 3;
// 变量提升示例
console.log(a); // undefined(var 提升)
// console.log(b); // ReferenceError(let 暂时性死区)
// const 不可重新赋值
// c = 4; // TypeError
const obj = { name: 'test' };
obj.name = 'new'; // ✅ 允许,修改的是引用内部属性
箭头函数核心特性
箭头函数是 javascript面试 中的高频考点,其核心特性包括:没有自己的 this(继承外层作用域的 this)、不能作为构造函数(无 prototype)、不能用 call/apply/bind 改变 this、不支持 arguments 对象(需用剩余参数替代)。
// 箭头函数 this 继承外层
function Person() {
this.age = 0;
setInterval(() => {
this.age++; // ✅ this 指向 Person 实例
}, 1000);
}
// 箭头函数无 prototype
// const fn = () => {};
// fn.prototype; // undefined
// 箭头函数不能用 new
// const fn = () => {};
// new fn(); // TypeError
面试中常考箭头函数与普通函数在 this 指向上的差异,以及何时应该使用箭头函数(如回调函数、事件处理中保持 this 一致性)。
Promise 链式调用与静态方法
Promise 是 javascript面试 中异步编程的核心考点。需要掌握 Promise 的三种状态(pending、fulfilled、rejected)、链式调用中 then 的返回值传递、以及 Promise.all / Promise.race / Promise.allSettled / Promise.any 四个静态方法的适用场景差异。
// Promise.all - 全部成功才成功
Promise.all([promise1, promise2]).then(results => {
// results = [result1, result2]
}).catch(err => {
// 任意一个失败即进入 catch
});
// Promise.race - 竞速模式
Promise.race([promise1, promise2]).then(first => {
// 哪个先 resolve 就返回哪个
});
// Promise.allSettled - 全部完成(ES2020)
Promise.allSettled([promise1, promise2]).then(results => {
// results = [
// { status: 'fulfilled', value: ... },
// { status: 'rejected', reason: ... }
// ]
});
手写 Promise 实现也是 javascript面试 中的经典题目,需要理解状态机、微任务调度、链式调用中 then 的返回值处理等核心逻辑。
async/await 与错误处理
async/await 是 ES2017 引入的语法糖,让异步代码看起来像同步代码,极大提升了可读性。在 javascript面试 中,面试官常考察 async/await 与 Promise 的等价关系、try-catch 错误处理机制、以及并行请求的优化写法。
// 串行请求
async function fetchUserOrders() {
try {
const user = await fetchUser();
const orders = await fetchOrders(user.id);
return orders;
} catch (error) {
console.error('请求失败:', error);
}
}
// 并行请求(性能更优)
async function fetchUserAndOrders() {
try {
const [user, orders] = await Promise.all([
fetchUser(),
fetchOrders()
]);
return { user, orders };
} catch (error) {
console.error('请求失败:', error);
}
}
ES6 Class 与原型继承
ES6 的 class 语法本质上是原型继承的语法糖。在 javascript面试 中,需要理解 class 的继承机制、super 关键字的用法、静态方法、私有字段(# 前缀)等特性,以及 class 与构造函数+原型链方式的等价关系。
class Animal {
constructor(name) {
this.name = name;
}
speak() {
return `${this.name} makes a noise.`;
}
static create(name) {
return new Animal(name);
}
}
class Dog extends Animal {
constructor(name, breed) {
super(name); // 调用父类构造函数
this.breed = breed;
}
speak() {
return `${this.name} barks.`;
}
}
const dog = Dog.create('Rex'); // 静态方法
console.log(dog.speak()); // "Rex barks."
Proxy / Reflect / Symbol 等高级特性
Proxy 和 Reflect 是 ES6 中较为高级的特性,常用于实现响应式系统(如 Vue 3 的 reactivity)、数据验证、日志追踪等。Symbol 用于创建唯一标识符。在 javascript面试 中,这些知识点通常出现在中高级前端岗位的面试中。
// Proxy 基本用法
const handler = {
get(target, prop) {
console.log(`获取属性: ${prop}`);
return target[prop];
},
set(target, prop, value) {
console.log(`设置属性: {value}`);
target[prop] = value;
return true;
}
};
const proxy = new Proxy({}, handler);
proxy.name = 'test'; // 输出: 设置属性: name = test
console.log(proxy.name); // 输出: 获取属性: name
// Reflect 与 Proxy 配合
const obj = { name: 'test' };
const proxy = new Proxy(obj, {
get(target, prop) {
return Reflect.get(target, prop);
},
set(target, prop, value) {
return Reflect.set(target, prop, value);
}
});
Proxy 是 Vue 3 响应式系统的核心实现基础,了解 Proxy 与 Object.defineProperty 的区别(Proxy 可以监听数组变化、新增属性等)是面试加分项。
三、Vue / React 框架面试题精解
在现代前端开发中,Vue 和 React 是最主流的两个框架。在 javascript面试 中,框架相关的题目往往占据较大比重,以下是两个框架各自的高频考点。
Vue 响应式原理与生命周期
Vue 2 使用 Object.defineProperty 实现响应式,Vue 3 使用 Proxy。面试中需要掌握:数据如何被监听、依赖收集与通知更新的过程、setter/getter 的作用。生命周期方面,需要熟记 created、mounted、updated、destroyed 等钩子函数的执行时机及适用场景。
// Vue 2 响应式核心逻辑(简化版)
function defineReactive(obj, key, val) {
const dep = new Dep();
Object.defineProperty(obj, key, {
get() {
if (Dep.target) {
dep.addSub(Dep.target); // 依赖收集
}
return val;
},
set(newVal) {
if (newVal !== val) {
val = newVal;
dep.notify(); // 通知更新
}
}
});
}
Vue 3 的响应式系统基于 Proxy,优势在于可以拦截对象属性的新增和删除,无需像 Vue 2 那样使用 Vue.set / Vue.delete 来处理动态属性。
Vue Router 与 Vuex / Pinia
Vue Router 的 hash 模式与 history 模式原理、路由守卫(beforeEach、beforeEnter、beforeRouteEnter)、嵌套路由、动态路由是 javascript面试 中 Vue 方向的高频考点。状态管理方面,Vuex 的 state/getters/mutations/actions/modules 机制,以及 Pinia 相比 Vuex 的优势(更简洁的 API、更好的 TS 支持)都需要掌握。
React 组件生命周期与 Hooks
React 16.8 引入 Hooks 后,函数组件成为主流。面试中需要掌握 useState、useEffect、useContext、useReducer、useMemo、useCallback 等常用 Hooks 的原理与使用场景,以及自定义 Hooks 的编写方法。同时需要理解函数组件与 class 组件生命周期的对应关系。
function Counter() {
const [count, setCount] = useState(0);
// useEffect 模拟 componentDidMount + componentDidUpdate
useEffect(() => {
document.title = `Count: ${count}`;
// 清理函数模拟 componentWillUnmount
return () => {
console.log('清理副作用');
};
}, [count]); // 依赖数组
return (
<div>
<p>Count: {count}</p>
<button onClick={() => setCount(c => c + 1)}>+1</button>
</div>
);
}
React 性能优化与虚拟 DOM
React 的虚拟 DOM diff 算法、key 的作用、React.memo、useMemo、useCallback 的性能优化手段是 javascript面试 中的重点。需要理解 React 的调和(Reconciliation)过程,以及为什么 key 对列表渲染性能至关重要。
四、前端工程化与构建工具
前端工程化是 javascript面试 中高级岗位的重要考察方向,涉及构建工具、模块化、包管理、代码规范等多个维度。
Webpack 核心概念
Webpack 是前端构建工具的标杆,面试中常考 Loader 与 Plugin 的区别、Entry/Output/Module/Chunk/Asset 五大核心概念、Code Splitting 实现方式(动态 import、SplitChunksPlugin)、HMR(热模块替换)原理等。
常见的 Loader:babel-loader(JS 转译)、css-loader/style-loader(CSS 处理)、url-loader/file-loader(资源文件)、eslint-loader(代码检查)。
常见的 Plugin:HtmlWebpackPlugin(生成 HTML)、MiniCssExtractPlugin(CSS 提取)、TerserPlugin(代码压缩)、DefinePlugin(环境变量注入)。
Vite / Rollup / Turbopack
Vite 基于 ES Module 实现极速开发服务器,生产构建使用 Rollup。面试中需要理解 Vite 为什么比 Webpack 快(利用浏览器原生 ES Module、预构建依赖),以及 Vite 的插件系统与 Rollup 插件的兼容性。
Turbopack 是 Vercel 推出的 Rust 构建工具,旨在替代 Webpack 提供更快的构建体验。了解这些新兴工具能展现你对前端技术趋势的关注。
五、前端性能优化实战指南
性能优化是区分初级与高级前端开发者的关键能力之一。在 javascript面试 中,性能优化相关的题目往往能直接反映候选人的工程实践经验。
加载优化
代码分割(Code Splitting)、懒加载(Lazy Loading)、Tree Shaking、CDN 加速、HTTP/2 多路复用、资源压缩(Gzip/Brotli)、图片优化(WebP/AVIF 格式、懒加载、响应式图片)、预加载(preload/prefetch/preconnect)等策略都是加载优化的核心手段。
渲染优化
减少重排(Reflow)和重绘(Repaint)、使用 CSS3 动画(GPU 加速)、虚拟列表(Virtual Scroll)处理大数据量渲染、防抖(Debounce)和节流(Throttle)优化高频事件、requestAnimationFrame 替代 setTimeout 实现流畅动画。
性能指标监控
掌握 Core Web Vitals 三大指标:LCP(最大内容绘制)、FID(首次输入延迟)、CLS(累积布局偏移)。使用 Performance API、Lighthouse、WebPageTest 等工具进行性能分析与优化。
内存优化
避免全局变量污染、及时清理事件监听器和定时器、使用 WeakMap/WeakSet 存储弱引用、避免闭包导致的内存泄漏、定期使用 Chrome DevTools Memory 面板分析堆快照。
| 优化方向 | 具体策略 | 影响指标 | 实现难度 |
|---|---|---|---|
| 资源加载 | 代码分割 + 懒加载 | FCP、LCP | ⭐⭐ |
| 资源加载 | 图片 WebP 格式 + 懒加载 | LCP、CLS | ⭐ |
| 渲染性能 | 虚拟列表 | FID、FPS | ⭐⭐⭐ |
| 渲染性能 | 防抖/节流 | FID | ⭐ |
| 缓存策略 | Service Worker + Cache API | FCP、LCP | ⭐⭐⭐ |
| 构建优化 | Tree Shaking + 压缩 | FCP | ⭐ |
六、javascript面试 高频算法题解析
算法题是 javascript面试 中筛选候选人编程能力的重要手段。以下整理了最常出现的算法题型及其解题思路。
数组去重
面试中最基础的算法题之一。常见解法包括:Set 去重、filter + indexOf、reduce + includes。需要掌握各方案的优缺点及时间复杂度。
// 方法1:Set(推荐)
const unique1 = [...new Set([1, 2, 2, 3])]; // [1, 2, 3]
// 方法2:filter + indexOf
const unique2 = arr.filter((item, index) => arr.indexOf(item) === index);
// 方法3:reduce
const unique3 = arr.reduce((acc, cur) => {
return acc.includes(cur) ? acc : [...acc, cur];
}, []);
深拷贝与浅拷贝
深拷贝是 javascript面试 中的经典题目。需要掌握 JSON.parse/stringify 的局限性(无法处理函数、undefined、Symbol、循环引用),以及手写递归深拷贝的实现。
function deepClone(obj, map = new WeakMap()) {
if (obj === null || typeof obj !== 'object') return obj;
if (map.has(obj)) return map.get(obj);
const clone = Array.isArray(obj) ? [] : {};
map.set(obj, clone);
for (let key in obj) {
if (obj.hasOwnProperty(key)) {
clone[key] = deepClone(obj[key], map);
}
}
return clone;
}
实现 Promise.all
手写 Promise.all 是 javascript面试 中的经典手写题。需要处理:所有 Promise 成功时返回结果数组、任意一个失败时立即 reject、空数组的特殊处理、保持输入顺序。
function promiseAll(promises) {
return new Promise((resolve, reject) => {
if (!Array.isArray(promises)) return reject(new TypeError('argument is not array'));
if (promises.length === 0) return resolve([]);
let results = [];
let count = 0;
promises.forEach((p, i) => {
Promise.resolve(p)
.then(res => {
results[i] = res;
count++;
if (count === promises.length) resolve(results);
})
.catch(reject);
});
});
}
防抖与节流
防抖(Debounce)和节流(Throttle)是前端性能优化的经典工具,也是 javascript面试 中必考的手写题。防抖指事件触发后等待一段时间再执行,若期间再次触发则重新计时;节流指单位时间内只执行一次。
// 防抖
function debounce(fn, delay = 300) {
let timer = null;
return function(...args) {
clearTimeout(timer);
timer = setTimeout(() => fn.apply(this, args), delay);
};
}
// 节流
function throttle(fn, interval = 300) {
let lastTime = 0;
return function(...args) {
const now = Date.now();
if (now - lastTime >= interval) {
lastTime = now;
fn.apply(this, args);
}
};
}
斐波那契数列
斐波那契数列是面试中常见的递归与动态规划题目。需要掌握朴素递归(O(2^n))、记忆化搜索(O(n))、迭代法(O(n))三种实现方式,并理解各自的时间复杂度和空间复杂度。
// 迭代法(最优)
function fibonacci(n) {
if (n <= 1) return n;
let prev = 0, curr = 1;
for (let i = 2; i <= n; i++) {
[prev, curr] = [curr, prev + curr];
}
return curr;
}
链表反转
链表反转是数据结构相关题目的经典代表。需要掌握迭代法和递归法两种实现,理解指针操作的核心逻辑。
// 迭代法
function reverseList(head) {
let prev = null;
let curr = head;
while (curr) {
const next = curr.next;
curr.next = prev;
prev = curr;
curr = next;
}
return prev;
}
七、javascript面试 实战技巧与准备策略
掌握知识点只是第一步,如何在 javascript面试 中有效展示自己的能力同样重要。以下从准备到实战的全流程策略,帮助你最大化面试成功率。
面试前准备清单
- 系统梳理 javascript面试 高频知识点,建立知识框架图
- 准备 2-3 个有深度的项目案例,用 STAR 法则(情境、任务、行动、结果)组织语言
- 刷 LeetCode 剑指 Offer / Hot 100,重点掌握数组、字符串、链表、树、动态规划等题型
- 准备自我介绍(1 分钟和 3 分钟两个版本),突出与前端开发相关的技能和经验
- 了解目标公司的技术栈和业务方向,针对性准备相关问题
- 准备反问环节的问题,展现对岗位和技术的热情
面试中应对策略
回答问题时:先给出结论,再展开说明原理,最后结合实际应用场景。如果遇到不会的问题,不要直接说"不知道",可以尝试分析思路,展现你的思考过程。
手写代码时:先理清思路再动手,边写边解释你的思考过程。注意边界条件处理(空值、异常输入等),写完代码后主动提出优化方案。
项目经验介绍:重点突出你在项目中解决的技术难点、性能优化成果、团队协作经验。用数据量化你的贡献(如"将首屏加载时间从 3s 优化到 1.2s")。
八、javascript面试 常见高频问题深度解答
以下整理了求职者搜索 javascript面试 时最常提出的问题,并给出详细的解答,帮助读者全面理解相关知识点。
在 javascript面试 中,ES6+ 最常考察的特性包括:
- let / const:块级作用域、暂时性死区、const 的不可变性边界
- 箭头函数:this 继承、无 prototype、arguments 替代方案
- 模板字符串:多行字符串、表达式插值、标签模板
- 解构赋值:对象解构、数组解构、默认值、重命名
- 扩展运算符:数组合并、对象合并、函数参数展开
- Promise:链式调用、静态方法、错误处理、手写实现
- async/await:与 Promise 的等价关系、并行请求优化、错误处理
- Class 类:继承、super、静态方法、私有字段
- 模块化:import/export、默认导出与命名导出、循环依赖
- Map / Set:与 Object / Array 的区别、迭代方式
- Proxy / Reflect:响应式原理、数据劫持、与 Object.defineProperty 的区别
- Symbol:唯一标识符、内置 Symbol、迭代器协议
原型链是 javascript面试 中的核心概念,准备时需要掌握以下要点:
- 原型对象:每个构造函数都有 prototype 属性,指向原型对象
- __proto__:每个对象都有 __proto__ 属性,指向其构造函数的 prototype
- constructor:原型对象上的 constructor 属性指回构造函数
- 原型链查找:访问属性时,先在自身查找,找不到则沿 __proto__ 向上查找,直到 Object.prototype
- instanceof:判断构造函数的 prototype 是否出现在对象的原型链上
- Object.getPrototypeOf():ES6 标准方法,获取对象的原型
- 原型继承:通过修改 prototype 或 Object.create() 实现继承
- ES6 Class:语法糖,底层仍是原型继承
建议通过画图的方式理解原型链结构,并通过手写各种继承模式来加深理解。
Event Loop 的执行顺序是 javascript面试 中的经典考题。核心规则如下:
- 同步代码 按顺序立即执行
- 宏任务(setTimeout、setInterval、I/O、UI 渲染)放入宏任务队列
- 微任务(Promise.then、MutationObserver、queueMicrotask)放入微任务队列
- 每次事件循环:执行完所有同步代码 → 执行所有微任务 → 执行一个宏任务 → 执行所有微任务 → ...
记忆口诀:"同步→微任务→宏任务→微任务→宏任务..." 每次宏任务执行完毕后,优先执行完所有微任务,再进入下一个宏任务。
在 javascript面试 中,算法题的准备可以分为以下几个层次:
- 基础题:数组去重、排序、反转、最大值/最小值、斐波那契数列、阶乘等
- 数据结构题:链表反转、合并有序链表、二叉树遍历(前中后序、层序)、栈/队列实现
- 动态规划:最长递增子序列、背包问题、爬楼梯、打家劫舍等
- 字符串处理:回文判断、最长无重复子串、括号匹配、字符串压缩
- 手写工具函数:深拷贝、防抖节流、Promise.all、柯里化、发布订阅模式
建议从 LeetCode 剑指 Offer 系列开始,每天保持 1-2 题的练习量,重点理解解题思路而非死记硬背。
项目经验是 javascript面试 中最能体现开发者实战能力的部分。回答时建议采用 STAR 法则:
- S(Situation)情境:简要描述项目背景和目标
- T(Task)任务:说明你在项目中承担的具体职责
- A(Action)行动:详细描述你采用的技术方案、解决的难点、优化的手段
- R(Result)结果:用数据量化成果(性能提升百分比、用户增长、bug 减少等)
准备 2-3 个项目案例,每个案例至少能说清楚 3 个技术亮点。避免泛泛而谈,要突出你在项目中的独特贡献和技术深度。
虽然 javascript面试 以 JS 为主,但 CSS 也是前端面试的必考内容。需要掌握:
- 布局:Flexbox、Grid、BFC 原理及应用场景
- 定位:static/relative/absolute/fixed/sticky 的区别
- 盒模型:标准盒模型 vs IE 盒模型(box-sizing)
- 选择器优先级:!important > 内联 > ID > 类/属性/伪类 > 标签
- CSS3 新特性:动画、过渡、渐变、变换、自定义属性(CSS Variables)
- 响应式:媒体查询、rem/vw/vh 单位、Flex/Grid 响应式方案
十、javascript面试 知识体系全景图
系统化的知识体系是顺利通过 javascript面试 的根本保障。以下从基础到进阶,梳理了前端开发者需要掌握的核心知识模块。
第一阶段:JavaScript 基础
数据类型、变量声明、运算符、流程控制、函数、作用域、闭包、this 指向、原型链、事件机制、DOM 操作、BOM API、异步编程基础。
第二阶段:ES6+ 新特性
let/const、箭头函数、模板字符串、解构赋值、扩展运算符、Promise、async/await、Class、模块化、Map/Set、Proxy/Reflect、Symbol。
第三阶段:框架与生态
Vue(响应式、生命周期、Router、Vuex/Pinia)、React(Hooks、虚拟 DOM、状态管理)、Angular(可选)、小程序开发。
第四阶段:工程化与工具
Webpack/Vite 配置、TypeScript、Git 工作流、代码规范(ESLint/Prettier)、CI/CD 流程、包管理(npm/yarn/pnpm)。
第五阶段:性能与优化
加载优化、渲染优化、内存管理、Core Web Vitals、Lighthouse 分析、性能监控、懒加载、代码分割、缓存策略。
第六阶段:算法与数据结构
数组/字符串操作、链表、树、排序算法、动态规划、递归、手写工具函数(深拷贝、防抖节流、Promise)、常见设计模式。