前端进阶之旅前端进阶之旅
  • 基础篇HTML/CSS/JS 打底
  • 进阶篇原理与工程化
  • 高频篇面试最常问的那批
  • 精选篇按模块收敛的总结
  • 手写篇常考代码手写实现
  • 面经篇真实面试问题复盘
  • AI 篇NEWAI 时代的前端考点
  • 历年面经NEW按年份追踪真实考点
  • 每日一题每天一道,攒手感
  • 专项自测100 题快速查漏
  • 小程序题库小程序专项刷题
  • 算法题库NEW在线编码即时判题
  • 知识卡片NEW碎片时间过考点
  • 面试题大全常见问题解析
  • AI 答疑NEW随时提问,即时解析
  • AI 模拟面试NEW模拟真实面试 + 报告
  • AI 定制路线NEW按你的简历现排
  • AI 知识地图NEW串起全站知识点
  • 原理篇React / Vue 源码拆解
  • HTTP从报文一路讲到 HTTPS
  • 浏览器渲染、事件循环、进程
  • 计算机基础Linux、网络、操作系统
  • 设计模式23 种模式怎么用
  • Node学习指南从环境搭建到服务端
  • NPM工作流script、依赖与发布
  • Docker容器化部署上手
  • Canvas图形与动画实战
  • 前端系统进阶学习大型项目工程化
  • 前端综合文章长期沉淀的实践文
  • 思维导图知识点全景图
  • 学习路线按图索骥不跑偏
  • AI 热点NEWAI 每日动态
  • 公众号动态公众号历史文章
  • 博客动态站长的技术博客
  • 开发者导航常用工具与文档站
  • 基础篇HTML/CSS/JS 打底
  • 进阶篇原理与工程化
  • 高频篇面试最常问的那批
  • 精选篇按模块收敛的总结
  • 手写篇常考代码手写实现
  • 面经篇真实面试问题复盘
  • AI 篇NEWAI 时代的前端考点
  • 历年面经NEW按年份追踪真实考点
  • 每日一题每天一道,攒手感
  • 专项自测100 题快速查漏
  • 小程序题库小程序专项刷题
  • 算法题库NEW在线编码即时判题
  • 知识卡片NEW碎片时间过考点
  • 面试题大全常见问题解析
  • AI 答疑NEW随时提问,即时解析
  • AI 模拟面试NEW模拟真实面试 + 报告
  • AI 定制路线NEW按你的简历现排
  • AI 知识地图NEW串起全站知识点
  • 原理篇React / Vue 源码拆解
  • HTTP从报文一路讲到 HTTPS
  • 浏览器渲染、事件循环、进程
  • 计算机基础Linux、网络、操作系统
  • 设计模式23 种模式怎么用
  • Node学习指南从环境搭建到服务端
  • NPM工作流script、依赖与发布
  • Docker容器化部署上手
  • Canvas图形与动画实战
  • 前端系统进阶学习大型项目工程化
  • 前端综合文章长期沉淀的实践文
  • 思维导图知识点全景图
  • 学习路线按图索骥不跑偏
  • AI 热点NEWAI 每日动态
  • 公众号动态公众号历史文章
  • 博客动态站长的技术博客
  • 开发者导航常用工具与文档站
首页程序员面试题库copyWithin 数组方法 高效场景
JSJavaScript数组与集合

copyWithin 怎样在数组内部复制,源目标重叠会覆盖错吗?

copyWithin 适合在同一容器里搬一段值,重点是它的范围复制语义,而不是承诺比任何循环都快。

前端进阶之旅 · 一题精讲更新于 2026.09.06
JavaScript#数组与集合#性能优化
先看核心答案读代码示例
理解线索

先标出源范围和目标范围

  1. 源片段从 start 读取到 end 之前
  2. 目标起点从 target 开始覆盖已有位置
  3. 有效数量同时受源长度和目标剩余空间限制

这是覆盖复制,不是插入或剪切。源范围的值不会因为被复制就自动移除,其他引用持有者会看到原数组变化。

核心回答

先记住这个答案

copyWithin(target, start, end) 把当前数组某段范围复制到同一数组的目标位置,修改原数组并返回它,长度不变,超出尾部的复制会被截断。源范围包含 start、不包含 end,支持相对负索引。源和目标重叠时,方法按能保留预期源序列的方向执行,效果不能照搬一个随手写的正向赋值循环。它复制的是元素值或引用,不删除源项,也不是深拷贝;稀疏位置还有属性删除语义。是否更快应在实际数据类型和引擎上测量,不能只凭内建方法名称推断。

  • 同一数组内部复制,长度不变
  • 重叠范围有明确定义的复制方向
  • 省去显式切片不等于所有场景都更快

重叠范围不能用直觉逐项覆盖

示例把零到二之前的两个值复制到索引一。若手写正向循环先改索引一,再拿已被改写的索引一覆盖二,就会得到错误的重复值;copyWithin 的重叠规则避免这个问题。

可以把预期理解为从原源片段取得对应序列再覆盖,但规范实现不要求真的分配一份中间数组。对用户而言应验证最终内容、长度和身份,避免把解释模型误写成内部实现保证。

源目标重叠时保留原片段语义JavaScript
const values = ['A', 'B', 'C', 'D'];
const returned = values.copyWithin(1, 0, 2);
console.log(JSON.stringify(values));
console.log(returned === values, values.length);
console.log(JSON.stringify([1, 2, 3, 4].copyWithin(3, 0, 3)));
查看输出与解释
["A","A","B","D"]
true 4
[1,2,3,1]

重叠复制得到 A、B 两个原始源值,而不是连续传播 A。第二例目标只剩一个位置,所以只覆盖最后一项,不会把数组长度扩展成六。

选择它之前确认需要覆盖而不是增删

维护固定容量缓冲或复用临时数组时,原地覆盖可能符合需求;编辑列表若要插入新记录并移动后续项,则应使用对应插入或重建操作。copyWithin 不会替业务增加空位或保留被覆盖数据。

状态管理里原数组可能被多个组件共享,原地修改会改变所有持有者看到的值。需要不可变更新时应先设计容器复制,并确认元素引用是否也需隔离,不能为了少分配而破坏更新契约。

普通数组、空位与性能要分别分析

复制对象元素时只复制引用,修改目标对象的内部字段仍可能影响源位置。普通稀疏数组若源位置不存在,对应目标属性可被删除,而不是简单写入 undefined,因此属性结构也应纳入测试。

密集数组、稀疏数组和 TypedArray 有不同约束与优化路径。热路径应比较耗时、内存和数据规模,方法可以减少手工范围处理的错误,却不能提供一个跨所有引擎的固定性能倍率。

回答前,多想一步

容易答错的地方

以为 copyWithin 复制后源片段会消失
它执行覆盖复制,不是剪切移动,源值仍可能保留在原位置。若业务需要删除或重新排列记录,应先写出期望数组,再选择对应操作,避免遗漏重复项和被覆盖数据。
手写正向循环替换却不处理重叠
目标落在源范围右侧时,早期写入会改变后续读取,导致同一个值被不断传播。应根据重叠方向选择读取顺序或使用明确快照,并通过重叠与非重叠用例验证结果。
试着用自己的话回答

面试官还会怎么问?

copyWithin 返回新数组吗?

返回的是被修改的当前数组,长度保持原值。链式写法不会让它变成不可变操作,调用方应检查共享引用和后续排序等方法是否继续修改同一个容器。

负数 target 表示什么?

它按数组长度换算为相对位置,再受合法范围约束。实际复制数量还取决于目标到尾部的剩余空间,因此不能只看源范围长度就断言会复制全部元素。

复制后的对象元素能独立修改吗?

不能自动独立,源和目标可能指向同一对象。若需要独立状态,应在复制规则中明确创建新对象或复制必要字段,容器内部位置变化不等于对象身份发生变化。

从一道题,走向一组知识

把知识连起来

数组与集合

concat 与数组展开怎样合并数组,为什么嵌套和空位结果不同?

比较内部覆盖与返回新容器的数组合并。

数组与集合

Array.fill 的负数 start、end 怎样换算,为什么最后一项没有被填?

对照范围写入同一值与复制一段不同值。

参考资料

  • MDN:copyWithin

示例用于理解所注明的运行环境与边界;延伸学习可结合原文中的更多案例。

本题目录
  1. 先记住这个答案
  2. 重叠范围不能用直觉逐项覆盖
  3. 选择它之前确认需要覆盖而不是增删
  4. 普通数组、空位与性能要分别分析
  5. 容易答错的地方
  6. 面试官还会怎么问
  7. 把知识连起来
读懂,再试着讲出来

先看核心答案,再读代码。最后展开追问,检查自己有没有遗漏边界。

试着回答追问
浏览全部面试题理解原理,也关注真实的使用场景。回到顶部 ↑