面试真题
JavaScript 基础
1. 已知 a = [1,2,3];求 console.log(a.push(5)) 的值是?为什么?
答案: 输出结果为 4
解析:
push()方法会向数组末尾添加一个或多个元素,并返回修改后数组的新长度a.push(5)会将 5 添加到数组[1,2,3]中,数组变为[1,2,3,5]- 返回值为新数组的长度,即
4 - 注意:
push()方法会修改原数组
let a = [1, 2, 3];
let result = a.push(5);
console.log(result); // 4
console.log(a); // [1, 2, 3, 5]
2. 数组排序方法除 sort 排序外还有哪些?并写出其中一种排序方法?
其他排序方法:
- 冒泡排序(Bubble Sort)
- 选择排序(Selection Sort)
- 插入排序(Insertion Sort)
- 快速排序(Quick Sort)
- 归并排序(Merge Sort)
- 堆排序(Heap Sort)
- 计数排序(Counting Sort)
示例:快速排序实现
function quickSort(arr) {
// 递归出口
if (arr.length <= 1) {
return arr;
}
// 选择基准值(中间位置)
const pivotIndex = Math.floor(arr.length / 2);
const pivot = arr.splice(pivotIndex, 1)[0];
// 定义左右数组
const left = [];
const right = [];
// 分区操作
for (let i = 0; i < arr.length; i++) {
if (arr[i] < pivot) {
left.push(arr[i]);
} else {
right.push(arr[i]);
}
}
// 递归排序并合并
return quickSort(left).concat([pivot], quickSort(right));
}
// 测试
const arr = [5, 2, 8, 1, 9, 3];
console.log(quickSort(arr)); // [1, 2, 3, 5, 8, 9]
事件处理与防抖节流
3. 常用的防止按钮多次点击触发的方案有哪些?并说明他们的区别?
常见方案:
方案一:防抖(Debounce)
function debounce(fn, delay = 300) {
let timer = null;
return function(...args) {
clearTimeout(timer);
timer = setTimeout(() => {
fn.apply(this, args);
}, delay);
};
}
// 使用
button.addEventListener('click', debounce(handleClick, 300));
方案二:节流(Throttle)
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);
}
};
}
// 使用
button.addEventListener('click', throttle(handleClick, 300));
方案三:标志位控制
let isClicked = false;
button.addEventListener('click', function() {
if (isClicked) return;
isClicked = true;
handleClick();
// 根据业务需求重置标志位
setTimeout(() => {
isClicked = false;
}, 1000);
});
方案四:禁用按钮
button.addEventListener('click', function() {
button.disabled = true;
button.textContent = '处理中...';
handleClick().finally(() => {
button.disabled = false;
button.textContent = '提交';
});
});
区别对比:
| 方案 | 特点 | 适用场景 |
|---|---|---|
| 防抖 | n 秒内只执行最后一次,重新触发会重置计时器 | 搜索框输入、窗口 resize |
| 节流 | n 秒内只执行一次,时间间隔固定 | 滚动加载、按钮点击频率限制 |
| 标志位 | 简单直接,需手动控制状态重置 | 简单的防重复提交 |
| 禁用按钮 | 用户体验好,直观显示状态 | 表单提交、异步请求场景 |
安全与性能优化
4. 前端常见的攻击方式有哪些?
(1)XSS(跨站脚本攻击)
原理: 注入恶意脚本代码到网页中执行
防御措施:
- 对用户输入进行 HTML 实体编码
- 使用 CSP(内容安全策略)
- 设置 HttpOnly Cookie
- 使用现代框架的自动转义功能
// XSS 攻击示例
// 用户输入:<script>alert('xss')</script>
// 应该转义为:<script>alert('xss')</script>
function escapeHtml(str) {
const map = {
'&': '&',
'<': '<',
'>': '>',
'"': '"',
"'": '''
};
return str.replace(/[&<>"']/g, m => map[m]);
}
(2)CSRF(跨站请求伪造)
原理: 诱导用户在已登录状态下访问恶意网站,执行非预期操作
防御措施:
- 使用 CSRF Token
- 验证 Referer/Origin 头
- 使用 SameSite Cookie 属性
- 关键操作要求二次验证
(3)点击劫持(Clickjacking)
原理: 使用透明 iframe 覆盖在正常页面上,诱导用户点击
防御措施:
- 设置 X-Frame-Options 响应头
- 使用 CSP 的 frame-ancestors 指令
- JavaScript 检测页面是否被嵌入
(4)SQL 注入(通过前端接口)
原理: 通过构造特殊输入参数,攻击后端数据库
防御措施:
- 前端验证输入格式
- 后端使用参数化查询
- 最小权限原则
(5)文件上传漏洞
原理: 上传恶意文件(木马、病毒等)
防御措施:
- 限制文件类型和大小
- 文件重命名
- 存储到非 Web 目录
- 扫描文件内容
5. 前端网站常规优化方案有哪些?
(1)网络层面优化
- 减少 HTTP 请求数:合并 CSS/JS 文件、使用雪碧图
- 使用 CDN 加速:静态资源分发到就近节点
- 开启 Gzip/Brotli 压缩:减少传输体积
- HTTP/2:多路复用,提升并发性能
- 预加载/预获取:
<link rel="preload" href="style.css" as="style">
<link rel="prefetch" href="next-page.js">
(2)资源优化
图片优化:
- 使用 WebP 格式
- 懒加载(Lazy Load)
- 响应式图片(srcset)
- 适当压缩
代码分割:
// React 路由懒加载
const HomePage = lazy(() => import('./HomePage'));
// Vue 路由懒加载
const routes = [
{ path: '/home', component: () => import('@/views/Home.vue') }
];Tree Shaking:移除未使用的代码
(3)渲染优化
- 减少重排重绘:
- 避免频繁操作 DOM
- 批量修改样式(使用 className)
- 使用 transform 替代 top/left
- 虚拟列表:长列表只渲染可视区域
- 防抖节流:高频事件优化
- requestAnimationFrame:替代 setTimeout 做动画
(4)缓存优化
- 浏览器缓存:
- 强缓存:Cache-Control, Expires
- 协商缓存:ETag, Last-Modified
- 本地存储:
- localStorage/sessionStorage
- IndexedDB(大数据量)
- Service Worker:离线缓存
(5)构建优化
// webpack 配置示例
module.exports = {
// 生产环境压缩
optimization: {
minimize: true,
splitChunks: {
chunks: 'all',
cacheGroups: {
vendors: {
test: /[\\/]node_modules[\\/]/,
name: 'vendors'
}
}
}
},
// 移除 console.log
terserOptions: {
compress: {
drop_console: true
}
}
};
(6)性能监控
- Performance API:
performance.getEntriesByType('navigation')[0]; - Lighthouse:自动化性能审计
- Web Vitals:监控核心性能指标(FCP、LCP、FID、CLS)
(7)用户体验优化
- 骨架屏:加载占位
- 渐进式加载:优先加载核心内容
- 错误边界处理:友好的错误提示
- PWA:离线可用、可安装