项目介绍

Adrian0314/cet6-cihui-shuati 是一个托管在 GitHub 上的开源项目,主要使用 HTML 编写,目前获得 8 个 Star、1 次 Fork。

仓库全名
Adrian0314/cet6-cihui-shuati
Star 数
8
Fork 数
1

README 摘要

🎓 英语六级词汇刷题系统 一个面向日常复习的 CET-6 词汇刷题系统。词库取自两本刘晓艳纸质教辅书(大纲词汇 6,363 词 + 核心词汇 3,324 词),另收录一份《英语六级核心 1500 词(2026 年 6 月)》词表(1,500 词),按书中 Unit 顺序、词群结构与艾宾浩斯打卡表排程复习,支持 PWA 安装到手机/电脑,像原生 App 一样全屏使用。 🔗 开始刷题(推荐):https://adrian0314.github.io/cet6-cihui-shuati/cet6quiz.html 手机浏览器打开 → 菜单/分享 →「添加到主屏幕」,即可全屏使用。 为什么值得用 📖 详解全覆盖 —— 6,363 + 3,324 条词条的「🧠 巧记 + 💬 例句」覆盖率均达 100%,另附派生词、易混淆词辨析与词群导图 🎤 跟读练习 —— 听标准发音、检测目标词匹配、录音回放与自评,练习记录自动保存 🎯…

完整内容见 GitHub 原始 README 或本页 。

常见问题

cet6-cihui-shuati 用什么语言开发?

主要使用 HTML 编写,目前有 8 个 Star。

如何获取 cet6-cihui-shuati 的源码?

可以直接克隆仓库:git clone https://github.com/Adrian0314/cet6-cihui-shuati.git,默认分支为 master;安装与运行步骤见仓库 README。

cet6-cihui-shuati 最近还在维护吗?

仓库最近一次更新为 5 天前,当前没有未关闭的 Issue;Star 数为 8,可作为社区活跃度的参考。

简要分析

热度分
10
价值分
5
活跃状态
活跃

语言占比

Batchfile
CSS
HTML
JavaScript

贡献者

README

🎓 英语六级词汇刷题系统

一个面向日常复习的 CET-6 词汇刷题系统。词库取自两本刘晓艳纸质教辅书(大纲词汇 6,363 词 + 核心词汇 3,324 词),另收录一份《英语六级核心 1500 词(2026 年 6 月)》词表(1,500 词),按书中 Unit 顺序、词群结构与艾宾浩斯打卡表排程复习,支持 PWA 安装到手机/电脑,像原生 App 一样全屏使用。

🔗 开始刷题(推荐):https://adrian0314.github.io/cet6-cihui-shuati/cet6_quiz.html 手机浏览器打开 → 菜单/分享 →「添加到主屏幕」,即可全屏使用。

为什么值得用

  • 📖 详解全覆盖 —— 6,363 + 3,324 条词条的「🧠 巧记 + 💬 例句」覆盖率均达 100%,另附派生词、易混淆词辨析与词群导图
  • 🎤 跟读练习 —— 听标准发音、检测目标词匹配、录音回放与自评,练习记录自动保存
  • 🎯 严格贴教材 —— 词库与复习排程都照抄纸质书,Unit 1-14 打卡表逐日逐项一致,不是拼凑词表
  • 💾 数据自主 —— 统计、错题、学习进度全存本地,支持导出备份 / 导入恢复 / 恢复出厂

目录:🚀 快速开始 · ✨ 功能特色 · 📚 词库 · 📖 使用指南 · 🗂 项目结构 · 🛠 技术栈 · 📄 License · 📝 更新与修复记录

🚀 快速开始

方式一:手机 / 浏览器直接使用

手机上点击这个链接 **https://adrian0314.github.io/cet6-cihui-shuati/cet6_quiz.html**,用浏览器打开,点击右上角三个点,点击 「添加到主屏幕」 即可在桌面快速点击使用(全屏运行)。

方式二:安装为 App(PWA)

  1. 部署到任意静态托管(GitHub Pages / Netlify / Vercel)
  2. 用手机浏览器打开链接:
    • 安卓:Chrome/Edge → 菜单 →「添加到主屏幕」
    • iPhone:Safari → 分享 →「添加到主屏幕」
  3. 安装后全屏运行,数据保存在当前浏览器

注意:PWA 安装需通过 https 地址访问,本地双击打开不支持安装。

方式三:打开下载的页面文件

进入仓库目录,双击 cet6_quiz.html 可浏览词库和做题。发音检测需要通过 HTTPS 网页或本机 HTTP 服务打开,不能使用 file://。

方式四:词群导图查看器(只看导图)

不想做题、只想浏览词群导图时使用——Unit 1-10 全部词群整树展示,不用一个一个点节点:

  • 在线版:https://adrian0314.github.io/cet6-cihui-shuati/word-maps-viewer.html
  • 单文件版:双击 word-maps-viewer-offline.html(数据已内联,单文件可拷到 U 盘/手机/别的电脑,无需网络)
  • 文件版:双击 word-maps-viewer.html(需与 unit-maps.js、core-words.js 同放一个目录)
  • 功能:Unit/词群下拉切换、🔍 搜索单词自动定位并高亮、点卡片朗读发音、点 ○ 折叠/展开分支、滚轮/双指缩放、拖拽平移、⬇ 导出 SVG/PNG;「◀ 上一个 / 下一个 ▶」导航条固定在底部图例上方独立成行,每次加载新词群初始视野自动以根节点为中心

词库/导图数据更新后,在仓库根目录运行 node build-core-words.js,再运行 node build-offline-viewer.js,可同步词库索引并重新生成单文件版。

方式五:词群编辑器(维护工具)

仓库附带词群导图编辑工具链,需本机安装 Node.js(建议 18+):

  1. 在仓库目录双击 打开词群编辑器.bat:自动检测词典服务端口(17989),未运行则拉起 node dict-server.js,随后在浏览器打开 word-map-editor.html
  2. 编辑器支持:从有道词典抓取单词讲解(服务未启动时尝试直连)、可视化编辑词群导图节点、保存回 unit-maps.js
  3. 也可单独双击 启动词典服务.bat 只启动服务;改完导图重新发布即可更新网站的词群导图

说明:dict-server.js 仅用 Node 内置模块(http/https/fs),无 npm 依赖;词典数据来自有道公开接口。

✨ 功能特色

功能 说明
🏰 闯关模式 严格对应书中使用指南:闯关1「词群速记」(认识/不认识快刷)、闯关2「选择检测」(Lesson 检测,选择题/默写题)、闯关3「Unit 综合测」(覆盖整个 Unit)
🧠 记忆模式 做完一题即从队列移除,答错的词按间隔自动排期回来复习
📅 艾宾浩斯记忆调度 大纲词汇采用「4周25天计划」(Unit 1-14 全部参与,按 +1/+3/+6/+11 天间隔);核心词汇与 1500 核心词按每词 8 格周期(5分/30分/12时/1天/2天/4天/7天)调度,到期自动横幅提醒一键清债。完成判定以实际作答为准:计划日的每个 Unit 只要全部单词都在本计划日内答过一遍——无论通过「开始复习」队列、记忆模式、普通「开始做题」还是智能练习——计划栏都会显示“当天目标已完成”;复习队列中断后重建时只推送还没答过的词,已练过的题不会整段重做。未完成的计划日跨天不清零:已完成的 Unit、没做完的题目和中断的做题队列都自动延续到第二天接着做,直到该日任务全部完成才进入下一天
🗺️ 词群导图 大纲词汇 Unit 1-10 全部启用书页真实导图:同词群单词的放射状关系图(中心=词群主题,节点=词),圆圈外侧绿色数字徽标=分支数,点击圆圈逐层下钻,点击单词朗读;导图未覆盖的词自动回退旧版导图
🗺️ 词群导图查看器 独立可视化页面:Unit 1-10 全部 173 个词群整树一次展示(非逐节点下钻),支持搜索定位、点击发音、折叠展开、缩放平移、导出 SVG/PNG;提供网页版与单文件版
🎯 三种题型 看中文选英文 / 看英文选中文 / 默写(智能近似判定)
✍️ 手写默写 手写板识别单词,结合词典自动纠错
❌ 错题本 & 重做 自动记录错题,支持搜索、按模式重做、答对自动移除
📖 单词详解 答完即学,单词浏览器点「查询」也能看:🧠 巧记(构词 / 联想 / 谐音 / 对照 / 提示)→ 💬 例句(英文句 + 空格 + 中文译文,两行显示)→ 🌱 派生词(同族词 + 音标,可朗读)。全部词条已配齐巧记与例句:核心词汇 3324 词、大纲词汇 6363 词覆盖率均达 100%(含书中 * 标注的派生词)
🔎 单词浏览器 「词库」标签按单元检索全部单词:默认 大纲词汇 Unit 1-14(6363 词),可切换 核心词汇 Unit 1-10(3324 词) 与 1500 核心词 List 1-50(1500 词);单元按钮逐个筛选,搜索支持中英文;每词可查询详解、查看词群导图、朗读发音、标记重点词(1500 核心词没有词群导图数据,该按钮不显示)
⭐ 重点词 做题时在单词标题/音标旁点击「☆ 标记重点」或「★ 已标记」添加/取消当前单词;状态同步到重点词列表和智能练习
🔇 智能混淆项 高频易混词优先作干扰项,答错时展示易混淆词辨析;英文→中文题的干扰项释义自动去重:与正确答案或其他选项共用核心汉字片段的同根词(如 可能/可能的、发明者/发明物)不会出现在同一道题中,当前单元内独立释义不足时从全库补足
🔊 朗读与自动朗读 手动朗读优先使用普通媒体音频(更适合蓝牙设备),失败时回退系统 TTS;可开启仅适用于“看英文→选中文”的逐题自动朗读
📊 详细统计 正确率、连对、每日热力图、近7天趋势、题型对比、词汇掌握情况、每日目标达标庆祝
📌 单元筛选 手动切换单元或全部单元(大纲词汇 Unit 1-14 / 核心词汇 Unit 1-10 / 1500 核心词 List 1-50);做题队列为当前筛选范围内的全部单词
📊 做题进度 做题时直接显示整轮做题进度:进度条标出已完成、当前和未完成题目,当前题固定显示在进度条中间;翻题或按题号跳转后自动跟随
⌨️ 快捷键 数字 1-4 选答案、空格跳过、回车下一题、←/→ 切换上一题/下一题、↑/↓ 滚动页面(电脑端,做题页与词库/错题本/统计等标签页都可用,全屏模式下同样生效);手机端做题页左右滑动切换上一题/下一题(全屏与非全屏均可用,记忆模式除外)
💾 数据自主 统计/错题/学习进度全存本地;4 周计划同日刷新或退出后可从「继续做题」或「开始复习」续做,支持导出备份、导入恢复、恢复出厂
🎤 发音练习 标准发音、目标词匹配检测、录音回放、自评与练习记录

📚 词库

词库 出处 内容
📗 大纲词汇 刘晓艳《英语六级你还在背单词吗》(东北师范大学出版社) 6,363 词。Unit 1-10「词以群记·抓核心」:词汇按词群分类(1,904 词),大多含记忆方法(联想/构词/对照/谐音)、经典例句,部分附扩展词;Unit 11-14「词以序记·刷基础」:大纲基础词按首字母分组——U11 A-E(1,240 词)、U12 E-M(1,254 词)、U13 M-S(1,299 词)、U14 S-Z(668 词),这两个单元均按纸质书页逐词核对,全部含音标与释义
📚 核心词汇 刘晓艳《六级英语核心词·艾宾浩斯抗遗忘打卡》(开明出版社) 3,324 词。10 个 Unit、每个 Unit 4 个 Lesson,每词按书中 8 格打卡周期调度
🎯 1500 核心词 《英语六级核心 1500 词(2026 年 6 月)》(用户提供的 PDF/JSON 词表) 1,500 词。50 个 List × 30 词(List 44-50 为「考前必备高分词」),全部含音标与释义;同样按每词 8 格周期调度。本词库没有巧记 / 例句 / 派生词,也没有词群导图数据

音标来源:两本纸质教辅的音标(含「单词详解」里的派生词音标)统一取自有道词典(英式优先、无英式时回退美式),不再混用 OCR 识别值与不同词典体系的窄式音标。13,220 条单词音标与 1,500 余条内联派生词音标已全部核验;个别教材自造的派生词不会凭空生成读音。1500 核心词的音标来自原始 PDF 文本层,并已修正 54 处 OCR 误识(ɪ 被识别成 r、ø 误识等)——每一处都用 PDF 文本层与本站另两套词库交叉比对、多来源一致才采纳。

📖 使用指南

开始做题

做题页从上到下依次设置:词库 → 单元筛选 → 闯关模式 → 做题模式 → 题目类型 →(可选)记忆模式 / 自动朗读,然后点「▶ 开始做题」。

  • 做题模式:看中文→选英文 / 看英文→选中文
  • 题目类型:选择题(四选一,遇到已知缺失释义的词条会自动修复显示,例如 animal 会显示“动物”)/ 默写题(键盘输入或手写板)
  • 重点词:做题时在单词标题与音标右侧点击「☆ 标记重点」或「★ 已标记」添加/取消当前单词;切换题目后按钮会跟随当前单词并保留状态,状态也会同步到重点词列表和智能练习
  • 做题进度与定位:做题时直接显示整轮答题进度,顶部进度条中绿色表示已完成,灰色表示未完成,青绿色高亮表示当前题;切换上一题、下一题或输入题号跳转时会自动滚动跟随当前题,当前题固定显示在进度条中间(首尾题也居中)。非全屏翻题时,题卡会定位到吸顶导航栏下方,避免手机端导航遮住题面首行或全屏按钮
  • 中途退出:做题进行中会即时把当前题位、已答数量和已选答案写入本地存储;手机切到后台、刷新页面或关闭网页时,页面生命周期事件还会再次保存,重新打开后点击顶部「继续做题」即可接着完成同一队列。手机从其他应用返回后,恢复保护会忽略浏览器补发的旧「不会,跳过」事件:首次真实点击选项可正常作答,只有实际按下跳过按钮才会执行跳过;跳过点击还必须落在真实起手之后 1.5 秒内,且起手必须发生在切回前台之后,补发的旧触摸(含完整序列重放)会被整事件取消,切后台很久再回来时点击选项不会被误判为跳过,跳过按钮也不会无故闪动。4 周 25 天计划会同时保存当日进度,复习提醒也会显示实际的已完成题数和待完成题数;当天新 Unit 的全部单词学完后会记录为已完成,不会再生成同一 Unit 的整组复习;复习队列中断后重新开始时只推送当天尚未答过的词,已练过的题不会重复出现;进入新的一天后,前一天已完成的任务按作答记录补判并正常推进到下一天,而前一天未完成的任务会被清空进度并强制整份重做,当天不能改做原定当天的计划;已答完但来不及清除的旧队列也会在重进时自动丢弃。
  • 朗读发音:点击单词旁的喇叭按钮优先使用普通媒体音频,以便跟随视频/音乐的蓝牙输出;网络音频无法播放时自动回退到系统 TTS,网络不可用时仍可使用系统 TTS
  • 自动朗读:在练习设置中切换「自动朗读:开/关」,开关会保存到本机;开启后仅在“看英文 → 选中文”时,每显示一道新题朗读一次,不会因答题反馈或局部刷新重复朗读。若浏览器限制非用户操作播放,可使用题面旁的朗读按钮
  • 答题后信息顺序:提交答案或跳过后,题目与正确答案下方紧接默认展开的“📖 单词详解”(巧记、例句、派生词);随后显示“⚠️ 易混淆词”辨析和词群归属信息,最后显示“🗺️ 词群导图”。点击标题可收起或重新展开单词详解内容。

🏰 闯关模式

关卡 名称 用法 适用场景
闯关1 词群速记 认识/不认识二选一快刷:认识直接进入下一词,不认识先展示默认展开的单词详解,再显示词群导图。快捷键 1/空格=认识,2=不认识 首次接触新词群,快速过一遍混个脸熟
闯关2 选择检测 标准四选一 / 默写题,答完即显示详解 学完一个 Lesson 后的检测
闯关3 Unit 综合测 一次覆盖整个选中 Unit 的全部词 学完一个 Unit 后的综合检测

取题量:每个闯关的做题队列都是当前筛选范围内的全部单词(闯关1/2 按书中顺序,重做模式为全部错题乱序)。做题中切换闯关模式会先保存当前进度。

🗺️ 词群导图

答完题自动显示当前词的词群关系图(单词浏览器点「🗺️ 导图」按钮也可查看)——中心=词群主题或当前词,四周圆圈=关联词:

  • 分支徽标:圆圈外侧的绿色数字徽标表示该词下面还有几个分支;点击带徽标的圆圈逐层展开,没有徽标的圆圈=末端词(无分支),点击朗读发音
  • 连线颜色:绿=派生(扩/合成)、蓝=同根、橙=近义、红=反义、粉=形近、灰=相关,虚线=形近/反义
  • 覆盖范围:大纲词汇 Unit 1-10(书页真实导图);导图未覆盖的词自动回退旧版导图

🧠 记忆模式

点「🧠 记忆模式」按钮开启,做题时做完一题即从队列移除,答错的词按当前词库的书中记忆规律自动排期回来复习:

  • 每次进入记忆模式的队列 = 到期复习词 + 当前选中范围内的未学新词
  • 做完一题即删,不回头重复;答错词进入记忆调度,到期自动回来

记忆规律:

  • 大纲词汇 → 「4周25天计划」(Unit 1-14 全部参与):第 1-14 天每天新学一个 Unit,之后按 +1天/+3天/+6天/+11天 间隔复习,第 15-25 天只做复习(如第9天学 Unit 9 并复习 Unit 3、6、8;第14天学 Unit 14 并复习 Unit 3、8、11、13;第25天复习 Unit 14 收尾)。每日 Unit 顺序逐日照抄纸质打卡表,见下方「📅 4周25天计划」完整表
  • 核心词汇 → 书中每词 8 格周期:5分/30分/12时/1天/2天/4天/7天

到期复习:

  • 打开网页时若有到期单词,做题页顶部显示绿色复习横幅,点「开始复习」四选一快刷一键清债,跳过视同答错
  • 5分/30分 这类短周期在学习会话内实时提醒
  • 4 周 25 天计划的完成判定以实际作答为准:当前计划日的每个 Unit 全部单词都答过一遍(不限做题入口),计划栏即显示「当天目标已完成」
  • 未完成当天计划:不清空进度、不强制重做——计划停留在该日,已完成的 Unit 和没做完的题目(含中断的做题队列)自动延续到第二天,接着上次继续;昨天的作答记录照常有效,直到该日任务全部做完,才在下一次跨天结算时进入下一天(计划栏显示「⏳ 该日计划尚未完成,进度延续中」)

📅 4周25天计划(Unit 1-14)

每行第一个 Unit 是当天新学,其余是当天要复习的 Unit(严格照抄刘晓艳《你还在背单词吗》书末「艾宾浩斯抗遗忘复习打卡表」):

天 计划 天 计划 天 计划
第1天 Unit 1 第10天 Unit 10、4、7、9 第19天 Unit 8、13
第2天 Unit 2、1 第11天 Unit 11、5、8、10 第20天 Unit 9、14
第3天 Unit 3、2 第12天 Unit 12、1、6、9、11 第21天 Unit 10
第4天 Unit 4、1、3 第13天 Unit 13、2、7、10、12 第22天 Unit 11
第5天 Unit 5、2、4 第14天 Unit 14、3、8、11、13 第23天 Unit 12
第6天 Unit 6、3、5 第15天 Unit 4、9、12、14 第24天 Unit 13
第7天 Unit 7、1、4、6 第16天 Unit 5、10、13 第25天 Unit 14
第8天 Unit 8、2、5、7 第17天 Unit 6、11、14
第9天 Unit 9、3、6、8 第18天 Unit 7、12

Unit 11-14 是按字母分组的基础词区(U11 A-E 1,240 词 / U12 E-M 1,254 词 / U13 M-S 1,299 词 / U14 S-Z 668 词),词量远大于词群区,因此第 11、13、14、15 天等含基础词区的日子单日题量会明显偏高(如第 11 天合计 1,755 题)。全部 6,363 词保留,不做删减。

注意:记忆模式是独立于闯关等级的学习方式开关,开启后按记忆调度自动排程(不按页取题);复习只从首次作答开始计,历史数据不迁移。

⌨️ 快捷键

  • 数字 1-4:选择题选答案
  • 空格:跳过(闯关1 中为「认识」)
  • 回车:下一题
  • 2:(闯关1 中为「不认识」)
  • ← / →:上一题 / 下一题(记忆模式除外)
  • ↑ / ↓:向上 / 向下滚动页面(电脑端;每次约 15% 视口高度,带平滑动画)。 全屏做题、词库、错题本、统计等页面都支持。焦点在输入框里时保持浏览器原生行为, 弹层(新手引导、复习提醒)打开时只滚弹层本身。

🗂 项目结构

前端已模块化拆分(2026-10 重构),源码按职责分目录存放:

README.md             项目说明
cet6_quiz.html        主程序入口(HTML 骨架 + 内嵌词库数据块)
├─ css/app.css        统一样式表(三层级联合并为单文件)
├─ vendor/chartjs.js  Chart.js 4.4.0 第三方库
├─ js/                应用逻辑模块(18 个文件,按职责拆分)
│   ├─ data.js            词库加载与索引(ALL_WORDS / FULL_WORDS / C1500)
│   ├─ theme.js           主题切换(白天/黑夜,View Transitions API)
│   ├─ state.js           localStorage 状态管理 + 规范化迁移
│   ├─ words.js           单词查询、词性、释义清洗
│   ├─ distractors.js     选择题干扰项生成
│   ├─ quiz-engine.js     出题引擎、调度、记忆模式
│   ├─ save-resume.js     进度暂存与恢复、偏好持久化
│   ├─ gesture.js         手势闸门(切后台恢复防误触)
│   ├─ render.js          题卡渲染、词群导图、单词详解
│   ├─ charts.js          统计图表(雷达/热力图/趋势)
│   ├─ export-import.js   数据导出导入、频率统计 UI
│   ├─ events.js          事件绑定与 data-action 委托
│   ├─ tts.js             朗读发音(TTS + 媒体音频)
│   ├─ pronunciation.js    发音练习面板
│   ├─ skip-keyboard.js    跳过/键盘快捷键/滚动
│   ├─ handwrite.js       默写手写输入
│   ├─ browse.js           单词浏览器
│   └─ app.js             初始化与回顶按钮
full-words.js         外置打卡词库(核心词汇 3,324 词)
core1500-words.js     外置 1500 核心词库(2026 年 6 月,1,500 词 / List 1-50)
unit-maps.js          外置词群导图数据(Unit 1-10)
core-words.js         词库发音/释义索引(自动生成)
word-maps-viewer.html 词群导图查看器(在线版,外置数据)
word-maps-viewer-offline.html 词群导图查看器(单文件版,数据内联)
word-map-editor.html  词群导图编辑器(维护工具)
dict-server.js        本地词典抓取服务(node dict-server.js,端口 17989)
打开词群编辑器.bat     一键启动编辑器(自动拉起词典服务)
启动词典服务.bat       单独启动词典服务
manifest.json         PWA 应用清单
sw.js                 Service Worker(资源缓存,v46)
icon-192.png / icon-512.png / apple-touch-icon.png   应用图标
site-qrcode.png       网站二维码
build-core-words.js   构建脚本(生成词库索引 core-words.js)
build-offline-viewer.js 构建脚本(生成单文件版查看器)
scan_meaning_bugs.js  释义数据质量扫描工具
_lookup.js            单词查询小工具

构建脚本依赖说明:build-core-words.js、scan_meaning_bugs.js、scripts/mnemonic-maintenance.mjs 均通过正则读取 cet6_quiz.html 中内嵌的 <script type="application/json" id="data-all-words"> 数据块,该块在重构后保持原位不变。regression/ 目录下的回归测试依赖全局函数(quizState、speakWord、ensureFullWords、applyTheme、openPronPractice、_ppState 等),这些函数在模块拆分后仍挂在 window 上,契约不变。

释义扫描脚本用法:在仓库根目录运行 node scan_meaning_bugs.js。

回归测试用法:node --test regression/pronunciation-single-mode.test.mjs regression/mnemonics.test.mjs regression/mnemonics-browser.test.mjs regression/pronunciation.test.mjs(需先 npm i -D @playwright/test playwright 安装浏览器)。

测试文件不入库:Playwright 用例(*.spec.js)与 Python 回归脚本(test_*.py)只在本地保留, 已在 .gitignore 中忽略,不会被提交或推送。下方修复记录里提到的用例名与运行命令, 指的是当时本地跑过的测试,仓库中不包含这些脚本。

🛠 技术栈

原生 HTML + CSS + JavaScript(无框架)、Chart.js 4.4.0(vendor 目录)、Vosk WASM、MediaRecorder、Web Audio / 系统语音、Service Worker、localStorage、Node.js(词群编辑器与构建脚本)、Python(音标数据维护)。

📄 License

MIT

📝 更新与修复记录

前端模块化重构(2026-10)

  • 拆分模块:将原 8,253 行单文件 cet6_quiz.html(含 ~7,100 行内联 JS、~800 行内联 CSS)拆分为 18 个 JS 模块(js/)+ 1 个统一样式表(css/app.css)+ Chart.js vendor 文件(vendor/chartjs.js)。cet6_quiz.html 保留为轻量 HTML 骨架(约 300 行),内嵌词库数据块不变。
  • 统一 CSS:将原有三层 CSS 级联(基础层 / Study Desk 刷新层 / Apple HIG 覆盖层)合并为单一 css/app.css(713 行)。设计令牌以 HIG 层为准(Apple 色板 + 空间节奏 + 半透明材质),消除三处重复 :root 块;所有组件样式完整保留。
  • 主题闪白修复:在 <head> 中增加阻塞脚本,首帧即读取 localStorage 并设定 data-theme,避免暗色模式下页面加载瞬间的白闪。
  • 移除内联事件处理器:将 21 处 onclick/oninput/onkeydown 替换为 data-action 属性委托(在 js/events.js 统一处理),HTML 中不再有任何内联 JS。
  • Service Worker:版本升级 v45 → v46;css/ js/ vendor/ 路径纳入 network-first 策略,保证发版后用户即时获取最新模块。
  • 回归验证:全部 27 项自动化测试通过(pronunciation-single-mode × 5 / mnemonics × 6 / mnemonics-browser × 3 / pronunciation × 13);localStorage 向后兼容,所有全局函数契约不变。

新增第三个词库:🎯 六级 1500 核心词(2026 年 6 月)

  • 数据:新增 core1500-words.js —— 1,500 词,50 个 List × 30 词 (List 44-50 为「考前必备高分词」),每词含音标与中文释义。采用与 full-words.js 相同的懒加载机制,Service Worker 缓存版本升到 v45, 老用户刷新即可取到新词库。
  • 词库逻辑重构:原先「core / full 两库」散落在十余处 === 'full' 判断里, 现收敛为一张 POOL_META 注册表(POOL_IDS / isKnownPool / isGridPool / poolLabel / poolUnitLabel / poolUnits),外置词库另加统一入口 ensurePool / poolWords / isPoolLoaded。以后再接新词库只需加一条元信息, 不必再逐处判断。
  • 适配:单元筛选与单词浏览器在该词库下按 List 1-50 展示(另两库仍是 Unit);复习沿用每词 8 格周期(5分/30分/12时/1天/2天/4天/7天); 错题、重点词、统计按词库隔离,存储键统一为 pool:id 并兼容旧数据迁移; 掌握度雷达在单元过多时自动合并区间(List 1-50 → L1-5 … L46-50 共 10 根轴)。
  • 边界:该词库没有巧记 / 例句 / 派生词,也没有词群导图数据,因此禁用新版 导图判定并隐藏「导图」按钮,避免出现空白或串用大纲词汇的导图。
  • 数据质量:1,500 条全部校验通过(id 恰为 1…1500、50 个 List 各 30 词、 无空音标 / 空释义 / 重复词);音标修正 54 处 OCR 误识,每处都以 PDF 文本层 与本站另两套词库交叉比对、多来源一致才采纳。
  • 验证:端到端 36 项(切换 / 筛选 / 出题 / 复习调度 / 统计 / 浏览器 / 刷新恢复)全通过,无 console 与 pageerror;仓库自带回归测试 27 项全通过。

按时间从新到旧记录功能调整与修复;历史实现不代表当前交互。当前发音练习测试位于 regression/,早期维护测试未全部提交。

发音练习简化(2026-10-07)

跟读面板统一为「听标准发音 → 录音 → 目标词匹配 → 回听 / 自评」流程,无需切换模式或填写服务连接信息。 识别由 Vosk WASM 处理,首次自动准备约 39 MB 资源;录音采集、识别与回放共用所选麦克风,关闭面板或换词会取消本轮处理。 详情见 发音练习使用说明。

录音对比第三轮:加本地人声检测(VAD),修掉"能听到自己却检测不到"

现象:用户反馈"录音对比里我能听到自己的声音,但系统仍然无法识别到"。

根因(两个问题叠加):

  1. 功能语义:录音对比 当时只有「录制 → 回放」,没有任何检测逻辑;
  2. 提示串台:面板上那句「已结束跟读,没有识别到内容」是**上一次点「开始跟读」**留下的,未随录音更新, 看起来就像"录音里检测不到人声"。

顺带发现并修掉的三个真实技术缺陷:

  • 解码不可靠:decodeAudioData 解 MediaRecorder 的 webm/opus 实测只解出 0.06 秒(文件 >1 秒且能正常回放), 以此做分析必然误报"没声音"→ 改为录音期间实时采集 20ms 音量包络(AnalyserNode),解码仅作兜底;
  • VAD 阈值取法错误:原来以"整体均值×2"为噪声底,说话占比高时阈值被顶到人声之上 → 改用低分位(20%)估噪声底,阈值 max(噪声底×3, 峰值×8%, 0.004),并加 0.6 倍迟滞;
  • 状态行串台:录音对比改用独立状态行 #ppRecStatus,与跟读互不覆盖。

现在的结论文案:✅「已检测到人声:约 x.x 秒,峰值 xx%,约 n 个音节段」(音量偏小会额外提示); ❌「未检测到清晰人声:录音里几乎只有底噪…」并给出靠近麦克风 / 调大音量 / 蓝牙改内置麦克风的建议; 并明确标注"本功能做本地人声检测,不做云端识别"。

验证:test_pron_practice_regression.py 扩到 15 项(新增⑭ VAD 纯函数三态判定—— 静音/人声/轻声,并断言"阈值不得高于峰值一半"以锁死历史缺陷;⑮ 端到端真实假设备录音判为已检测到人声); 全量 126 项测试通过;sw.js v35 → v36;排查指南更新第三轮(根因 + 三个技术缺陷 + 一句话排查口径)。

发音练习第二轮:区分"收不到声音"与"收不到识别结果"+三条独立通道

背景:用户反馈"耳机设置正常,浏览器仍收不到声音"。两张截图给出关键证据—— 自检电平曾显示 100%(设备其实在送声音),随后却又提示"没有输入"。 排查发现两个真实缺陷,以及一个更常见的环境事实。

缺陷一:静音判定用了瞬时值。原判断只看"判定那一刻"的电平,于是先说后停会被误报成 “一直没有声音输入”。→ 改为按整段最大电平判断,并区分"设备有声音 / 没有声音"两种结论去向。

缺陷二:自检与识别抢麦克风。电平表持有 MediaStream 的同时又启动语音识别, 蓝牙耳机(HFP)与单麦克风设备同时只能被一路抓取,很容易两边都拿不到干净音频。 → 检测/录音结束即释放,并在开始识别前主动释放(ppReleaseMic()), 新增回归测试 ⑫ 锁定"跟读期间不得继续持有麦克风流"。

环境事实:识别结果与麦克风是两件事。Chrome/Edge 的网页语音识别是云端服务, 网络受限时会只"听"不返回;Firefox 不实现该 API;Safari 走自有通道。 因此新增两条独立运行的替代通道:

  • 「🎚 检测麦克风」:只开麦看实时电平(6 秒),并给出结论——"有声音输入(设备与权限正常, 识别失败多半是识别服务/网络问题)"或静音提示;
  • 「⏺ 录音对比」:MediaRecorder 录下自己的朗读(最长 6 秒)并本地回放,配合标准发音与自评按钮, 不依赖任何云端服务。

还新增:面板内输入设备下拉框(≥2 个设备时出现;选择记在本机; deviceId 失效时自动清选择并回退系统默认,对应 OverconstrainedError/NotFoundError)。

验证:test_pron_practice_regression.py 扩到 13 项(新增:真实假设备下电平读数与释放、 跟读期间已释放麦克风、录音对比生成可回放地址;并适配"开始跟读前约 1 秒麦克风探测"的时序); 全量 124 项测试通过;sw.js v34 → v35;排查指南更新为第二轮(含输出设备对录音的影响、 页面内输入源选择、驱动与占用、跨浏览器差异、逐步验证清单)。

发音练习增强:麦克风自检(实时输入电平)+ 具体错误提示

背景:用户反馈「耳机能听声音,但网页录音收不到麦克风」——站点只回了一句"没有识别到内容", 无法区分是环境问题(设备/权限)还是功能问题。排查确认其后来自系统侧: Windows「设置 → 系统 → 声音 → 输入」把蓝牙耳机的「允许应用和 Windows 将此设备用于音频」设为了不允许, 而它同时是默认输入设备,于是任何应用都收不到声音(详见 浏览器录音-麦克风排查指南-20261006.md)。

站点改动:

  • 面板新增 「输入电平」实时自检条:开始跟读时用 getUserMedia 取流 + AudioContext/AnalyserNode 画实时电平;说话时条会动,不动就说明声音没进来(一眼区分环境问题与功能问题);
  • 错误分类提示:把 NotAllowedError / SecurityError、NotFoundError、NotReadableError、 OverconstrainedError 等翻译成可执行的中文提示(改哪里的权限、检查哪个设备);
  • 不阻断识别:麦克风检查失败只提示原因,仍然尝试一次语音识别(权限刚放开时仍有成功机会);
  • 静音告警:2.5 秒内电平始终为 0 → 明确提示"麦克风一直没有声音输入",并列出三处必查设置 (系统默认输入设备、设备属性里的"用于音频"开关、蓝牙耳机是否处于免手操/通话模式);
  • 超时兜底:getUserMedia 1.5 秒不返回(设备弹窗挂起)时继续进入跟读,按钮不会像"没反应";
  • 结束时统一释放麦克风:停 requestAnimationFrame、关 AudioContext、stop() 所有 MediaStreamTrack。

验证:test_pron_practice_regression.py 扩到 11 项(新增:权限被拒给出具体提示且不阻断识别、 麦克风检查挂起不卡住跟读、真实假设备下电平表能读到声音且静音提示文案覆盖三处必查项); 全量 122 项测试通过;sw.js v33 → v34。

修复:「结束跟读」点了没反应(发音练习停止路径缺状态机)

  • 现象(用户截图):跟读进行中按钮显示「⏹ 结束跟读」、状态是「正在听…请朗读 void」, 点这个按钮后界面毫无变化,再点也没反应。
  • 根本原因(两条,均已复现):
    1. 停止路径没有自己的界面更新:ppListen() 在 listening 分支只调 rec.stop() 就 return, 按钮文案与状态文案全部依赖浏览器的 onend/onresult 回调。 一旦识别器不回调(麦克风权限弹窗挂起、识别服务无响应),界面就永远停在「正在听…」—— 点按钮"没反应"正是这个卡死状态。
    2. 状态标记与识别器生命周期脱钩:listening 只在 onend/onerror 里被置回 false, onresult(结果已出)里没有;stop() 后也不清 _ppState.rec。 于是「只给 onresult 不给 onend」的实现会让界面同时显示「✅ 发音正确」和「⏹ 结束跟读」, 此后每次点击都去打一个已结束的识别器 → 永久无反应。
  • 修复方案:
    • 新增跟读状态机标记 gotResult / stoppedByUser 与看门狗 watchdog,由本页自己维护;
    • 新增 ppStopListening(userInitiated):先立即把界面切到"已结束跟读,正在分析刚才的朗读…" (按钮→「🎤 再读一次」),再调 stop() 通知识别器;并设 1.2s 看门狗—— 浏览器不给结果就自行 abort() 收尾并提示「没有识别到内容,请再试一次」,界面不会再卡死;
    • onresult 里立即复位 listening 并取消看门狗(结果一到界面就恢复正常); onend/onerror 统一走 ppListenIdle() 复位并清理实例;ppFinish() 也复位, 不再出现「结果已出但按钮仍显示结束跟读」的假状态;
    • 开始新一轮前先 abort() 上一实例,避免 InvalidStateError 与旧回调串轮;
    • 关闭面板 / 点「读对了(自评)」/「再练一次」时,都先按"用户主动结束"收尾。
  • 时序验证(真机形态:stop() 后 60ms 才返回结果):点「结束跟读」→ 界面立刻复位 → 60ms 后拿到结果并显示「✅ 发音正确」;挂起形态:立刻复位 → 1.2s 后提示「没有识别到内容」→ 可继续下一轮。
  • 回归测试:test_pron_practice_regression.py 新增 2 项—— ⑦「识别器完全不回调时,点结束也必须立刻生效并可继续下一轮」; ⑧「只给 onresult 不给 onend 时不得残留假结束态」。全量 119 项测试通过;sw.js v32 → v33。

新功能:单词发音练习(跟读 + 语音识别比对),做题页与查单词都能用

  • 入口位置:就放在题面「🔊 朗读」按钮右侧(用户标注的红框处),与朗读同一行、高度完全一致(35px)、 略宽(87px → 129px),垂直居中对齐;查单词场景则在「单词详解」面板顶部提供同一对按钮。
  • 实现:pronPracticePillRow(word, ipa) 统一渲染两个按钮(.pron-pill 决定尺寸,发音练习加 .wide), 用 data-* + 事件委托绑定,避免把含撇号/引号的单词与音标拼进 onclick。
  • 练习流程:点开面板 → 自动播一遍标准发音 → 点「开始跟读」朗读 → 浏览器 SpeechRecognition 识别 → 自动比对(只保留字母,忽略大小写/空格/连字符/撇号):完全一致「✅ 发音正确」、 编辑距离 ≤25%「⚠️ 很接近」、差别大则回显识别到的读音。每个词的练习次数/读对次数记录在本机 (localStorage cet6_pron_practice_v1)。
  • 降级策略:浏览器不支持语音识别、未授权麦克风或网络不可用(not-allowed / service-not-allowed / network)时, 跟读按钮自动禁用并提示原因,改用「✅ 读对了(自评)/ 🔁 再练一次」,功能不失效。
  • 交互细节:点遮罩或 ✕ 或 Esc 关闭;关闭时中止识别;页面加载时预读语音列表逻辑不受影响。
  • 验证:新增 test_pron_practice_regression.py 6 项(两场景按钮存在与尺寸/对齐、识别正确、识别不符与接近、 不支持降级自评、两种关闭方式);全量 117 项测试通过;sw.js v31 → v32。

修复:释义被截断(C 选项显示「…等的复」)

  • 现象(用户截图):renaissance 的 C 选项显示「n. 尤指某种艺术形式、音乐形式等的复」, 句子在半截处停住、括号也没闭合。
  • 根因:词库早期按「释义 ≤20 字」的渲染规范裁剪释义时,是按字符数硬切的, 个别词条正好被切在词的中间——renaissance 原文是「(尤指某种艺术形式、音乐形式等的)复兴」, 切到第 20 个字时把「复兴」切成了「复」。这类截断在最早的数据导入阶段就存在(此前所有备份里都一样)。
  • 排查:写了两个精确判据扫全库 6,363 条—— ① 悬空尾巴:结尾是逗号/分号/顿号等连接性标点、或是裸露的词性残片(adj.、v、n)、或括号未闭合; ② 词中切断:站内释义是书中原文的前缀,且书中紧接着的字符不是分隔符 (借助 _mineru_audit/_all_entries.json 里的书中原文比对)。 命中 31 条(A 类 21 条 + B 类 10 条,如 board、dwell、gram、hour、seminar、shop、urge)。
  • 修复:不是简单恢复长句(会违反 ≤20 字的既有规范),而是在 20 字内把词补完整, 例:renaissance → n. (艺术、音乐等的)复兴;文艺复兴;gram → n. 克(公制重量单位); board → n. 板;董事会 v. 登上(车、机);shop → n. 商店;作坊;车间 v. 购买。
  • 校验:修复后全库 悬空尾巴 0 条、词中切断 0 条、释义超 20 字 0 条。
  • 回归测试:新增 test_text_sanity_regression.py::test_06_meaning_not_truncated(三类截断痕迹)。
  • 全量 111 项测试通过;core-words.js 已重建;sw.js v30 → v31; 明细见 释义截断修复清单-20261006.csv。

内容优化:把「外语/词源联想」巧记换成日常可操作的记忆线索(99 条)

  • 问题(用户反馈截图):plaza 的巧记是「联想 西班牙语 plaza 指广场 → 广场;购物中心」—— 线索是另一门语言。这类写法在真实背单词场景里不实用:回忆链条多一跳(plaza → 西语 → 广场), 任一跳断掉就调不出答案;外语读音还会干扰英语发音(menu /məˈny/、plaza /ˈplaθa/); 它只解释「为什么这样叫」,对拼写(Wednesday 的 d、knife 的 k、straight 的 gh)毫无帮助; 且词源多只对应古老义项,对考纲义项(magazine 只考「杂志」)无效。
  • 替换方案(七类日常线索):① 形近对照(与已学词差一个字母/同音/字母重排);② 英语内部词族 (锚点必须是已会的英语词);③ 高频搭配/场景句;④ 拼写拆段+发音规则;⑤ 中文谐音(画面含词义); ⑥ 语义链(多义词);⑦ 成对成组记。
  • 本次替换 99 条(涉及 U2-U14),典型改法:
单词 改前(依赖外语/词源) 改后(日常记忆线索)
plaza 联想 西班牙语 plaza 指广场 → 广场 构词 与 place(地方) 同族 → 城里的一片空地 → 广场;购物中心
October 联想 源自拉丁 octo(八) → 十月 联想 与 octopus(章鱼,八爪) 同前缀 oct-(八) → 罗马旧历第八月 → 十月
Wednesday 联想 源自古英语 Wodnesdæg(奥丁之日) 提示 拼写拆成 Wed-nes-day 三段来记,d 不发音 → 星期三
patrol 联想 法语 patrouille 对照 与 petrol(汽油) 只差一个字母 → 巡逻车要加油 → 巡逻,巡查
tail 提示 古英语 taegel 对照 与 tale(故事) 同音 → 故事总有个尾巴 → 尾巴;尾部
knife 联想 古英语 cnif 提示 拼写提示:k 不发音,读 /naɪf/;复数是 knives → 刀子,刀具
  • 保留原则:词源不是一律不能用,而是不能跨语言取线索——改锚到英语内部 (October↔octopus、December↔decimal、Monday↔moon、courage↔core),专名与常识 (marathon、Uranus)和高频词缀(anti-、ultra-、ex-)可以保留。
  • 验证:新增规则 test_memo_logic_regression.py::test_05_no_foreign_language_or_etymology_hook; 全库复查含外语名/词源叙述 0 条、缺抓手 0 条; 方案说明见 单词记忆法改进方案-20261004.md,逐条对照见 巧记-外语词源改日常记忆法-对照表-20261004.csv; 全量 110 项测试通过;sw.js v29 → v30。

内容优化:重写「没有记忆逻辑」的巧记 289 条(新增巧记必须带记忆抓手)

  • 问题(用户反馈截图):部分巧记只是把释义复述一遍,没有任何记忆原理—— 如 peg「联想 基础词,指钉、栓、桩、衣夹」、scare「提示 使害怕 → 恐慌,惊吓;使惊恐」、 ivory「联想 来自大象的白色长牙 → 象牙」。
  • 筛查规则(可验证、可回归):
    1. 以「基础词 / 常用词 / 本词…」这类模板套话开头;
    2. 巧记中没有任何抓手,且汉字与释义的重合度 ≥0.6(等于照抄释义)。
  • 新的编写标准(写入测试):每条巧记都必须含独立于释义的抓手,即 「英文部件或搭配」「引号里的谐音」「画面/场景描写」「词根词缀术语」「词形拆解符号(-、+)」五者之一; 禁止只复述释义。长度分层:构词 ≤55 字(要标词根含义)、含英文搭配的 ≤60 字、其余 ≤45 字。
  • 本次重写 289 条(U11-U14 共 281 条、U1-U10 共 8 条),典型改法:
单词 改前(复述释义) 改后(可理解的记忆原理)
peg 联想 基础词,指钉、栓、桩、衣夹 对照 与 leg(腿) 只差一个字母 → 立在腿边的木桩 → 钉,栓,桩;衣夹
mouth 联想 脸上的进食与发声器官 → 嘴;入口 对照 与 month(月份) 只差一个字母 → 每月都要张嘴吃饭 → 嘴;入口,入海口
needle 联想 细长尖物 → 针;针头;指针 构词 need(需要) + -le → 缝补必需之物 → 针;针头;指针
beard 提示 下巴上的毛发 → 胡须 联想 与 bread(面包) 字母重排 → 面包屑挂在胡须上 → 胡须;颔毛
aunt 提示 父亲的姐妹或母亲的姐妹 → 姑姑;阿姨 谐音 与 ant(蚂蚁) 同音 → 亲戚多得如蚂蚁 → 姑姑;阿姨,婶母
their 提示 形容词性物主代词,他/她/它们的 提示 与 they 配对:they 作主语,their 后面接名词 → 他们的
  • 说明:虚词与基础词(this/these、they/their/theirs、do、be 等)没有可拆的词根, 其记忆逻辑以配对/搭配为主(如 this 单数配 these 复数、they 作主语 their 接名词), 这属于「用法场景」型抓手,而非复述释义。
  • 验证:新增 test_memo_logic_regression.py(4 项:格式分层、每条都有抓手、无模板套话、 无抓手时不得照抄释义);全量 109 项测试通过;core-words.js 与本地查看器重建;sw.js v28 → v29。

修复:选项中文被逗号拆开(narrative 显示成「描述,叙,述,叙述的」)

  • 现象:narrative 的 B 选项显示「n. /adj. 描述,叙,述,叙述的」——「叙述」被逗号切成两个字。
  • 根因(两层):
    1. 数据:该词条释义为 n. 描述,叙 述 adj. 叙述的,其中「叙 述」夹了一个多余空格(录入噪声);
    2. 逻辑:getChineseOptionText() 末尾有一条「汉字+空格+汉字 → 补中文逗号」规则 (本意是把去掉词性标记后残留的义项片段分开,如 n.病房 v.防止,避免 → 病房,防止,避免)。 它无法区分「义项分界」与「词内噪声空格」,于是把「叙 述」也补成了「叙,述」。
  • 修复:
    • 数据:narrative 释义改为 n. 描述,叙述 adj. 叙述的;
    • 逻辑:getChineseOptionText() 开头先把词条自带的「汉字+空格+汉字」转成哨兵  (义项分界由词性标记决定,不受影响),函数末尾补逗号后再把哨兵直接连接—— 即「删掉噪声空格」而不是「补成逗号」,词内空格不会再被切开。
  • 影响面(实测全库 6,363 条逐条对比):显示文本只有 narrative 一条发生变化; 词性分界补逗号照常生效(989 条量级,如 病房,防止,避免);全库「词内空格被拆成逗号」违规 0 条。
  • 验证:新增 test_option_cjk_space_regression.py 5 项(narrative 不被拆分、词性分界补逗号保留、 全库不变量、纯词内空格应连接、显示文本未大面积变化);Python 全量 105 项通过;sw.js v27 → v28。

内容优化:重写 Unit 14 巧记(联想记忆)212 条 + 全单元格式统一

  • 问题:部分巧记联想突兀、缺逻辑关联——如 wharf「谐音沃夫 → 船靠岸之处 → 码头」、stove「谐音 发音类似"斯多夫"→炉子」,只给音译就跳释义,没有真正的记忆抓手;另有条目用「构词」标签写了非构词内容(如 theatre ← 同 theater 的英式拼写),以及大量讲长故事的超长条目(>45 字,最长 100+ 字)。
  • 筛查:按可验证规则扫 U11-14 共 4,461 条巧记,命中问题 950 条(Unit 14 占 212 条:谐音无桥 153 / 冗长 51 / 错拆 8)。
  • 本批修复 Unit 14 全部 212 条,并统一全单元格式(去掉 【构词】/[联想] 包裹写法、补齐统一前缀)81 条。
  • 新规范(5 类前缀 + 一行 ≤45 字):构词(词根词缀必须字面出现在词形中,容忍词干末尾 e 脱落)/谐音(发音贴近且画面含词义,禁止「发音类似 X → 释义」)/联想(形近词、同族词、高频搭配)/对照(近义/反义/同音/形近对比)/提示(拼写、读音、用法要点)。
  • 效果:Unit 14 巧记平均 30 字(改前 33,最长 100+),0 条缺前缀 / 超长 / 自指涉;类型分布 构词 332 / 联想 190 / 谐音 73 / 提示 46 / 对照 27。
  • 验证:Python 全量 92 项通过(含巧记格式规范测试);明细见 Unit14-巧记优化明细-20260925.md。
  • 待续:Unit 11(240 条)/ Unit 12(241 条)/ Unit 13(257 条)按同一规范分批重写。

修复:蓝牙耳机下个别单词从外放出声(朗读路径混用两种音频通道)

  • 现象:连接头戴式蓝牙耳机后,多数单词从耳机播放,个别单词(如 vigo(u)r)却从设备外放。
  • 根因:单词朗读有两条通道,且会互相切换——
    1. 在线媒体音频(new Audio('https://dict.youdao.com/dictvoice?audio=…'))走媒体输出路由,跟随蓝牙 A2DP 耳机;
    2. 在线音频失败时回退的系统 TTS(speechSynthesis)走系统语音通道,输出设备不跟随媒体默认设备。 词库里保留了书上的合并写法(vigo(u)r、hono(u)r、symbolic(al)、a/an、theatre/-ter 等共 34 个词条), 这些写法被原样送进音频接口会被拒(实测返回 HTTP 500 / 120 B JSON 错误),于是触发回退 → 输出设备随之改变。
  • 修复:
    • 新增 normalizeSpeakText():发音前把合并写法规范化为标准拼写(vigo(u)r → vigour、a/an → a、 theatre/-ter → theatre、photo(graph) → photograph),在线音频与系统 TTS 两条路径都使用规范化文本;
    • 在线音频失败时先在同一媒体通道内换英式音源重试(type=2 → type=1),仅当两个音源都不可达 才回退系统 TTS(纯本地兜底),把"切换输出设备"的概率降到最低;
    • 规则卡文案同步说明该策略。
  • 验证:修复前实测 vigo(u)r → HTTP 500(120 B JSON 错误),vigour → HTTP 200(28 KB mp3); 新增 test_tts_output_route_regression.py 4 项:规范化覆盖全部合并写法词条、朗读 vigo(u)r 时 实际请求 URL 为 audio=vigour&type=2、成功路径不触发系统 TTS、失败时先换英式音源重试; Python 全量 92 项通过。

词库调整:2026-09-24(五)删除「未分单元」补充词(313 词,6,676 → 6,363)

  • 背景:词库此前把书中未归入任何 Unit 的 313 个词作为「未分单元」补充词收录(选「全部」时参与刷题)。按用户要求一次性删除,词库只保留有明确单元归属的词。
  • 调整:
    • 删除全部 313 个无单元编号的词条(已备份到本地 _backup_unit0_removed.json);
    • 单词浏览器移除「未分单元」筛选按钮,以及对应的筛选与统计文案分支;
    • 规则卡与 README 词库说明同步(不再提及「未分单元」补充词);
    • 词库索引 core-words.js、本地导图查看器同步重建。
  • 结果:大纲词汇 6,676 → 6,363 词,Unit 1-14 每个词都有明确单元归属;各单元词数 U1 154 / U2 189 / U3 163 / U4 232 / U5 78 / U6 214 / U7 250 / U8 214 / U9 175 / U10 233 / U11 1,240 / U12 1,254 / U13 1,299 / U14 668。
  • 验证:Unit 1-14 合计 = 全库总数(无重复、无遗漏);「未分单元」筛选入口已移除;全库巧记 / 例句 / 词性标签断言通过;Python 全量 88 项通过(含 1 项滚动位置偶发抖动,单独重跑全过)。

词库调整:2026-09-24(四)按纸质书页重排 Unit 11(1,061 → 1,240 词,逐词核对)

  • 背景:Unit 11 原为「A-E」自动分段(1,061 词);按书上 P286-P301 的 16 页词汇表(Lesson 1-4)整体替换。至此 Unit 11-14 四个基础词区单元全部按纸质书页逐词核对完成(U11 1,240 / U12 1,254 / U13 1,299 / U14 668)。
  • 调整:
    • 933 个原有词条保留全部既有内容,只更新 lesson / seq(Lesson 1-4 = 318 / 324 / 290 / 308);
    • 66 个原「未分单元」补充词并入 Unit 11(affair、afraid、aftermath、altitude、amass、amuse 等);
    • 241 个词库此前缺失的词新增词条并补齐巧记与例句(advertisement、advertising、affect、arrest、artistic、assessment、badge、ballot、botanical、browse、brutal、cartoonist、cashier、cavity、cholesterol、chorus、clergy、colonial、conspiracy、consul、contamination、county、cradle、crystal、custody、dairy、devil、digital、diligence、dip、discreet、dizzy、doubtful、drought、dub、durable、dynasty、earnest、earnings 等),词库「详解覆盖率 100%」保持;
    • 128 个不在书页清单中的词移出 Unit 11 并删除(已备份)。
  • 同形异义词按书页拆成独立词条:bow(/bəʊ/ v.鞠躬) 与 bow(/baʊ/ n.弓;蝴蝶结);清单中两次出现的 can 拆为 can(/kæn/ aux.能,会) 与 can(/kæn/ n.金属罐 v.装罐;解雇)。
  • 拼写变体取英式主形式(adviser、apologise、airplane、centimetre、centre、disc、chairman、characterise、colonise、computerise);保留括号写法(behavio(u)r、colo(u)r、armo(u)r、blond(e)、cigaret(te)、dad(dy)、ax(e)、(a)esthetic、ag(e)ing、alphabetic(al)、among(st)、afterward(s)、counsel(l)or)。
  • 原书 OCR 错误修正:重复条目 arenn 合并入 arena;check /tʃi:k/ n.脸颊 按正确拼写录为 cheek。
  • 结果:Unit 11 = 1,240 词条;大纲词汇总数 6,563 → 6,676;「未分单元」补充词 379 → 313。
  • 验证:Unit 11 与清单逐词核对(1,240 条、无遗漏);各单元合计 + 未分单元 = 6,676;全库巧记 / 例句 / 词性标签 / 释义长度(≤20 字)断言全部通过;Python 全量 88 项通过。

词库调整:2026-09-24(三)按纸质书页重排 Unit 12(884 → 1,254 词,逐词核对)

  • 背景:Unit 12 原为「F-L」自动分段(884 词),与书上 P302-P317 的词汇表不一致;本次按 16 页清单(Lesson 1-4)整体替换。
  • 调整:
    • 868 个原有词条保留全部既有内容,只更新 lesson / seq(Lesson 1-4 = 299 / 318 / 310 / 327);
    • 211 个词从其他单元迁入:Unit 11 的 E 段 169 词(earth、east、economy、education、electric(al)、environment、equator、essay、ethnic 等按书页归入 U12)、「未分单元」41 词、Unit 7 的 mate 1 词;
    • 155 个词从 U13 / U14 重排时的删除备份恢复(含 M 段前半的 machine、magazine、mail、main、make、manage… 此前曾被移出词库,现归位到 U12);
    • 20 个新增词条(eventful、fasten、hectic、illicit、lighting、luncheon、mint、mister、mould、mouldy 等)并补齐巧记与例句;
    • 16 个不在书页清单中的词移出 Unit 12 并删除(已备份)。
  • 同形异义词按书页拆成独立词条(本次按你的要求处理):lead(v. /liːd/) 与 lead(n. 铅 /led/)、live(v. /lɪv/) 与 live(adj. 直播 /laɪv/)、lower(v. 降低 /ˈləʊə/) 与 lower(v. 变昏暗 /ˈlaʊə/)、minute(n. 分钟 /ˈmɪnɪt/) 与 minute(adj. 微小的 /maɪˈnjuːt/);March/march、May/may 按大小写区分为不同词条。
  • 结果:Unit 12 = 1,254 词条(含 4 组同形异义双条);大纲词汇总数 6,404 → 6,563;Unit 11 由 1,230 → 1,061 词;「未分单元」补充词 420 → 379。
  • 验证:Unit 12 与清单逐词核对(1,254 条、每行一条、无遗漏);各单元合计 + 未分单元 = 6,563;全库巧记 / 例句 / 词性标签 / 释义长度(≤20 字)断言全部通过;Python 全量 88 项通过。

词库调整:2026-09-24(二)按纸质书页重排 Unit 13(494 → 1,299 词,逐词核对)

  • 背景:Unit 13 原为「M-S」自动分段(494 词),与书页不一致;补齐了 Unit 13 的 16 页词汇表(P318-P333,Lesson 1-4,共 1,299 词)。
  • 调整:按清单整体替换该单元词表:
    • 316 个原有词条保留全部既有内容,只更新 lesson / seq(Lesson 1-4 与书页一致);
    • 57 个原在其他单元的词(多为「未分单元」补充词,如 municipal、mushroom、mystery、offer、oxygen、planet、random、remove、repair、restaurant、rocket 等)并入 Unit 13;
    • 887 个词此前因 Unit 14 重排被移出词库,本次从备份完整恢复(巧记 / 例句 / 派生词齐全);
    • 39 个全新词条(pace、pack、page、pain、paint、paper、paragraph、retaliate、romance、stout、storey 等)新增并补齐巧记与例句,词库「详解覆盖率 100%」保持;
    • 178 个不在书页清单中的词(machinery、mad、magazine、mail、main、make、manage 等 M 段前半词)随本次调整从 Unit 13 移出删除(已备份)。
  • 结果:Unit 13 = 1,299 词(L1 309 / L2 313 / L3 328 / L4 349);大纲词汇总数 5,656 → 6,404;「未分单元」补充词 476 → 420;Unit 3 因 pop 归入 Unit 13 变为 163 词。
  • 验证:Unit 13 与清单逐词核对(不多不少、无重复拼写);各单元合计 + 未分单元 = 6,404;全库巧记 / 例句 / 词性标签 / 释义长度(≤20 字)断言全部通过;Python 全量 88 项通过。

词库调整:2026-09-24 按纸质书页重排 Unit 14(1,518 → 668 词,逐词核对)

  • 背景:Unit 14 原为「P-Z 基础词区」的自动分段(1,518 词),与实际书页不一致,做题时该单元题量明显偏大。
  • 调整:按书上 Unit 14 的 8 页词汇表(Lesson 1 344 词 + Lesson 2 324 词,共 668 词)整体替换该单元词表:
    • 清单内的词条保留全部既有内容(巧记 / 例句 / 派生词),只更新 unit / lesson / seq(按书页顺序);
    • 20 个原「未分单元」补充词(superficial、supper、temperature、tissue、zone 等)并入 Unit 14;
    • 2 个英式拼写词条(tranquillity、tumour)由原美式拼写词条迁移数据;
    • 55 个书上原有、词库此前缺失的词(variety、vegetable、warning、width、weaken、wireless 等)新增词条并补齐巧记与例句,词库「详解覆盖率 100%」保持不变;
    • 其余 923 个不在书页清单中的词(P-R 及部分 T-Z 词,含 piano、picture、please、philosophy、value 等)随本次调整从 Unit 14 移出删除。
  • 结果:Unit 14 = 668 词(Lesson 1 / Lesson 2 与书页一致);大纲词汇总数 6,526 → 5,656;「未分单元」补充词 496 → 476。词库索引 core-words.js 与本地导图查看器已同步重建。
  • 验证:Unit 14 与清单逐词核对(不多不少);各单元合计 + 未分单元 = 5,656(无重复、无遗漏);全库巧记 / 例句 / 词性标签 / 释义长度(≤20 字)断言全部通过。

修复记录:2026-09-13 选项不显示词性(int./exclam./abbr. 未收录)+ 残缺释义补全

  • 问题:截图三题(pleasing / please / pleasure)中,please、hey 等选项没有词性标签。定位:选项词性由 wordPartOfSpeech() 扫描释义中的 xx. 标记产生,而词性白名单 POS_LABELS 未收录词库实际使用的 int.(please、hello、hey)、exclam.(hi、fuck)、abbr.(AD、BC、CD、DVD、etc),这些词因此整条选项无词性。
  • 修复(渲染层):
    1. POS_LABELS 增补 int / exclam / abbr;
    2. splitMeaning() 支持「前置括号注记 + 词性」写法((=phone) n.电话、( = burger) n.汉堡包、(=exam)n.考试):注记归入中文、词性照常生成 badge,修复 14 个带注记词条在题干/浏览器列表里缺词性的现象;
    3. getChineseOptionText() 增补斜杠清理,词性写法 n./v. 清洗后不再在中文里残留 /(patrol 曾显示「/ 巡逻,巡查」)。
  • 修复(数据层,17 个词条):补全只有词性或残缺的释义——airplane/chairman(原为音标残片)→ n.飞机 / n.主席;banana/carrot/season/semi-colon/normalisation/oceanic/falsehood 补词性与释义;useful 修 adj 缺句点与重复;can/could/might/shall/would 由 modal v. 统一为 aux.;patrol 由 n & v. 规范为 n./v.;pharmaceutical 去前导孤立「;」。
  • 验证:全库扫描 0 个选项缺词性、0 个缺词性释义段、0 个中文残留异常符号;新增 test_option_pos_regression.py 6 项(含截图三道题的选项词性断言);Python 全量 83 项通过,JS 相关用例经 HEAD 基线对比确认通过。sw.js 缓存版本 v12 → v13。

功能调整:2026-09-12 单词浏览器支持 Unit 1-14 全量检索 + 修复 repair 表超长释义覆盖

一、单词浏览器覆盖 Unit 1-14(此前仅核心词汇 Unit 1-10)
  • 问题:单词浏览器列表只遍历 FULL_WORDS(核心词汇 3324 词 / Unit 1-10), 大纲词汇 Unit 11-14 的基础词(以及书中未归单元的补充词)在浏览器中查不到。
  • 调整:新增词库切换——默认浏览大纲词汇 Unit 1-14(6526 词),可切换 核心词汇 Unit 1-10(3324 词,选择记忆在本地);新增单元筛选按钮(Unit 1-14 + 「未分单元」,核心词汇显示 Unit 1-10);列表顶部显示「共 N 个单词」, 搜索仍支持中文释义与英文单词;每词的查询 / 导图 / 朗读 / 标记重点按所属词库 正确归属(此前浏览核心词库时固定用 'full' 池,且打卡进度误用做题页 currentPool)。
  • 验证:Unit 1-14 每个单元筛出数量与数据源逐一核对一致,且各单元合计 + 未分单元 = 6526(无重复、无遗漏);14 个单元各抽样单词均能搜索命中并返回 含巧记 / 例句的详解。
二、修复 repairWordData 把长释义覆盖回页面(way 释义仍超长的真因)
  • 问题:词库数据已把超长释义精简到 20 字内,但 repairWordData 的已知问题 修复表里仍留着这些词的旧长释义,运行时逐词覆盖回去——way(189 字)、 sweet(193 字)、family(122 字)、bunch(70 字)、ought(58 字)、wall(24 字)、 disarm(22 字)、animal(21 字)共 8 个词在页面上依然显示超长释义。
  • 修复:清理修复表——数据已修正的词(way / bunch / family / sweet / ought / animal / their / hear / manoeuvre 及两个空标记)不再运行时覆盖;仅保留词库数据 确实残缺、必须运行时补齐的 7 条(fibre 去音标残片、tempo / intake / mineral / wall / disarm 补词性-only 的释义、optimum 补名词义避免与 optimal 重复), 并全部控制在 20 字内。
  • 新增回归:test_browse_all_units_regression.py——运行时全库释义 ≤20 字符、 浏览器 Unit 1-14 覆盖与计数、逐单元抽样查询返回详解、核心词库切换等 7 项。

巧记质量修订:2026-10-15

  • 先修订截图中的 flirt、foe、gear、fuss、gauge、glamor、foil、glamorous,再继续检查两套词库。本轮新增修订 765 个不同单词 / 862 条词条记录(大纲词库 750 条、核心词库 112 条),连同此前修订累计 975 个不同单词 / 1229 条记录。
  • 重点清理“与某词形近,然后直接给出释义”、仅重复中文释义、生词循环互引、牵强谐音、无依据的词根拆解,以及括号或句子残缺。改用具体动作、常见搭配、能够解释含义的构词或明确对照。
  • 例如 ceiling 通过“房间最上方的天花板”连接“价格上限”;comb 通过“梳齿细细梳过头发”连接“细致搜寻”;court 删除与 courage 的错误词根联系,改用法官在法庭审案的场景。live、bow、cast 等多义词分别给出常见用法,避免遗漏不同词义。
  • 两套词库保持 6363 / 3324 条记录,只修改巧记,释义、例句、派生词、词条顺序及其他字段不变。逐词清单 保留每条修订前的原文、修订理由与新巧记。
  • 维护脚本补充形近后跳释义、释义重复、同源标签和残缺文本的筛查。运行 node scripts/mnemonic-maintenance.mjs --audit 可生成待复核候选,规则命中不等于语义有误,仍需逐条审校;本轮不代表全词库已完成词源核验。
  • 验证:node scripts/mnemonic-maintenance.mjs、npm test。站点缓存版本升至 v44。

巧记质量修订:2026-10-07

  • 从 cruise 的无关音译问题出发,对两套词库做机械筛选和重点人工复核,修订 **202 个不同单词 / 359 个

README 内容过长,已截取前 64 KB。完整内容请前往 GitHub 仓库查看。

评论

暂无评论