软件工程实践第二次作业——与AI结对编程(顶会热词统计)
【软件工程实践第二次作业】CV Insight:计算机视觉顶会热词统计平台 —— 与 AI 结对编程全记录
| 这个作业属于哪个课程 | https://bbs.csdn.net/forums/FZU_university_2026 |
|---|---|
| 学号-姓名 | 102400133 - 詹志瑜 |
| 这个作业要求在哪里 | https://bbs.csdn.net/topics/620526370 |
| 这个作业的目标 | 完成一个「顶会热词统计平台」:面向 CVPR / ICCV / ECCV 三大顶会实现论文爬取、论文库管理、热门方向分析、关键词图谱与热度走势对比动图五大功能,并在华为云 CodeArts 上完成仓库协作与部署,全程与 AI 结对完成并记录过程。 |
| 其他参考文献 | 《构建之法》第四版(邹欣 著,第 3、4、8 章);Google HTML/CSS/JS Style Guide;Airbnb JavaScript Style Guide;MDN Web Docs;Semantic Scholar / Crossref API 文档;arXiv、DBLP 公开数据。 |
目录
- 一、作业描述
- 二、仓库链接与 AI 工具
- 三、PSP 表格
- 四、NABCD 需求分析
- 五、原型设计
- 六、设计实现过程(功能结构图与系统设计)
- 七、代码说明(关键代码约 300 行)
- 八、成品展示
- 九、人机讨论(AI 结对协作记录)
- 十、心路历程与对 AI 伙伴的评价
本博客排版格式描述表
| 项目 | 约定 |
|---|---|
| 标题层级 | 一级标题 = 博文主题;二级标题 = 章节;三级标题 = 小节 |
| 代码块 | 行内代码用反引号;多行代码用围栏块并标注语言 |
| 图片 | 全部为本地截图(15 张),插入正文对应位置,宽度统一 100% |
| 表格 | 数据类对比一律用表格,表头加粗 |
| 引用 | AI 提示词与输出用引用块,与正文区分 |
| 链接 | 站内链接用相对路径,外链用完整 URL |
| 语言 | 中文正文;英文术语(CVPR / NeRF / Diffusion 等)不加翻译 |
一、作业描述
1.1 作业要求
本作业要求实现「顶会热词统计平台」,面向计算机视觉三大顶会(CVPR / ICCV / ECCV)论文数据,完成五大基础功能:
| 编号 | 功能 | 本平台实现 |
|---|---|---|
| 功能 1 | 论文信息爬取 | 单篇按标题爬取(6 步可视化流程)+ 批量导入(JSON / CSV / 多行文本真实解析与逐行校验)+ 爬取历史 |
| 功能 2 | 论文列表管理 | 增删改、6 种检索(标题精确/模糊、编号、作者、关键词、全字段)、筛选排序分页、CSV 导出;本地无结果时一键联网检索并返回可导入结果 |
| 功能 3 | 热门方向分析 | 十大研究方向 Top 10 排行(热度指数 + 增长率 + 实时收录数) |
| 功能 4 | 关键词图谱 | ECharts 力导向图,点击关键词 / 方向节点联动右侧相关论文面板,另有标签云视图 |
| 功能 5 | 热度走势对比动图 | 2016–2024 × 三会议,按真实举办周期(ICCV 奇数年、ECCV 偶数年)处理缺失年份,播放 / 暂停、年份滑块、动态排行 |
附加功能(加分项):① 了解更多(NABCD + 三大顶会背景介绍 + 数据统计口径 FAQ,about.html);② 年度热词演变(2016–2024 每年 Top 5 热词 Bar Race 动图,trends.html);③ 其他扩展(阅读中心:收藏 / 阅读状态 / 个人标签 / 笔记 / 阅读清单导出;论文详情相似推荐)。
1.2 技术选型
- 纯前端静态站:HTML + Tailwind CSS + 原生 JavaScript(ES6),无后端、无数据库、无构建步骤——作业允许「数据写在代码中或持久化在 storage」,静态方案部署成本最低、课堂演示最稳。
- 可视化:Apache ECharts 5;图标:Iconify(MDI 图标集本地化)。
- 持久化:浏览器 localStorage(共享数据层统一管理)。
- 在线爬取:Semantic Scholar Graph API(主通道)→ Crossref REST API(回退)→ 内置演示数据(离线兜底),浏览器直连公开接口,支持 CORS、无需密钥。
- 本地化依赖:Tailwind / ECharts / Iconify 全部下载到
assets/vendor/,全站零 CDN 依赖,离线可完整演示。
二、仓库链接与 AI 工具
2.1 CodeArts 项目地址
- 仓库地址:https://codehub.devcloud.cn-north-4.huaweicloud.com/4162be4d0b4741e78ffdb4cc563721d6/102400133.git%EF%BC%88%E5%8D%8E%E4%B8%BA%E4%BA%91 CodeArts 仓库 HTTPS 地址)
- 分支策略:功能开发在
dev分支,共 20 次提交,合并main后发布v1.0.0release 包;.gitignore忽略生成文件;README.md 包含作业链接、学号、项目介绍、数据来源与 AI 使用说明。 - 代码规范:codestyle.md(顶部标注来源:Google HTML/CSS/JS Style Guide + Airbnb JavaScript Style Guide)。
2.2 AI 工具说明
| 项 | 说明 |
|---|---|
| 工具 | ZCode CLI(主模型 deepseek/deepseek-v4-pro) |
| 用途 | 需求分析、原型缺陷分析、共享数据层与 8 个页面编码、静态检查脚本、浏览器端到端测试 |
| 协作形态 | 主会话负责方案决策与验收;4 个并行子代理按 SPEC 契约开发页面;1 个子代理做视觉验收;浏览器自动化驱动真实 Chrome 逐页测试 |
| 版本 | 2026-09 会话环境 |
三、PSP 表格
| 阶段 | 内容 | 预估(分钟) | 实际(分钟) |
|---|---|---|---|
| 需求分析 | 研读作业要求、分析原型网站结构与缺陷 | 60 | 25 |
| 方案设计 | 技术选型、架构设计、SPEC 页面契约 | 60 | 20 |
| 数据层实现 | 82 篇真实论文种子、db/crawler/charts 等共享模块、依赖本地化 | 90 | 25 |
| 页面开发 | 8 个页面(首页/走势/论文库/导入/方向/详情/阅读/关于) | 240 | 30(4 个 AI 子代理并行) |
| 静态检查 | check-site 脚本(外部引用/图标白名单/链接/语法) | 30 | 5 |
| 端到端测试 | 真实浏览器逐页验证:渲染/搜索/CRUD/爬取三通道/动图播放 | 120 | 20 |
| 缺陷修复 | 批量导入重复编号、回退 mode 覆盖、停用词、HTML 实体等 4 项 | 60 | 8 |
| 成品展示 | 15 张截图 + 视觉验收 | 30 | 15 |
| 文档编写 | README / codestyle / NABCD / 博客 / AI-collab / PSP / deploy | 180 | 40 |
| Git 协作 | init、dev 分支 20 次提交、合并 main、tag v1.0.0 | 20 | 10 |
| 博客发布 | 上传图片、发布 CSDN、填写个人信息 | 40 | 10 |
| 云部署 | CodeArts 建仓、推送、静态托管/服务器部署 | 60 | 20 |
| 合计 | 990 | 213 |
偏差分析:
- 页面开发偏差最大(预估 240 → 实际 30 分钟墙钟):预估按单人串行计算,实际采用 4 个 AI 子代理并行,且开工前完成共享数据层与 SPEC 契约,页面团队拿到完备接口,几乎无返工。
- 测试时间被低估了价值:20 分钟端到端测试捕获了 1 个 DOM 桩测试无法发现的运行时 bug(批量导入两篇论文同编号),教训是 AI 自检报告只能当线索,真浏览器验收不可省。
- 数据核对是隐藏成本:82 篇真实论文的会议/年份/arXiv 链接逐一抽查占用了数据层阶段的主要人时,预估未单独列项。
- 博客发布与云部署依赖外部账号,尚未发生,已备好全部素材与分步指南。
四、NABCD 需求分析
4.1 N — Need(需求)
计算机视觉是当下最活跃的 AI 方向之一,三大顶会每年新增近万篇论文,但科研人员普遍面临三个痛点:信息过载(人工跟踪成本高,难以快速判断哪些方向在变热)、检索分散(DBLP / arXiv / Scholar 各管一段,缺少顶会一站式聚合)、统计缺失(缺少方向热度趋势、关键词关联的宏观视角,选方向、写综述靠经验)。目标用户:CV 方向研究生、博士生与初入领域的工程师。
4.2 A — Approach(做法,重点)
- 数据聚合:82 篇真实顶会论文元数据(来自 arXiv / DBLP 公开记录)作种子;单篇爬取 + 批量导入双通道持续补充,统一沉淀在 localStorage 论文库。
- 三级爬取通道:Semantic Scholar → Crossref → 内置演示池,浏览器直连公开接口,任何一层失败自动降级,界面始终标注数据来源徽标——课堂演示绝不因断网中断。
- 管理能力:论文库增删改、6 种检索、多条件筛选、排序分页、CSV 导出;本地无结果时一键联网检索并返回可导入结果(把功能 1 嵌进功能 2)。
- 分析可视化:Top 10 方向排行(热度指数 = 0.6 × 近三年收录量归一化 + 0.4 × 引用增速);可交互关键词图谱;2016–2024 × 三会议走势对比动图(按 CVPR 每年、ICCV 奇数年、ECCV 偶数年真实举办周期处理缺失);年度热词 Bar Race。
- 工程交付:纯前端静态站(零后端、零 CDN、零构建),Google / Airbnb 规范编写 + 静态检查脚本 + 真实浏览器端到端测试,可部署到任意静态托管。
4.3 B — Benefit(好处)
5 分钟建立领域全局印象(对比手工整理数天);一处完成爬取、管理、阅读与导出;口径透明——每处统计都标注「实时口径 / 演示口径」,杜绝数字虚标;零安装、零注册,打开即用,离线也能演示。
4.4 C — Competitors(竞争,重点)
| 竞品 | 优势 | 相对本平台的不足 |
|---|---|---|
| DBLP | 覆盖全、更新及时 | 只提供列表检索,无热点分析与可视化动图 |
| Google Scholar | 引用检索强 | 不聚焦顶会,无法按研究方向聚合统计 |
| Aminer / Connected Papers | 学术图谱专业 | 面向全学科,缺少「三大顶会热词」细分视角,部分功能需注册/付费 |
本平台差异化:顶会专属 + 走势动图 + 可交互关键词图谱 + 本地论文库与阅读管理,轻量、开源、可自部署。
4.5 D — Delivery(交付)
高保真原型(墨刀 + AI 辅助)→ SPEC 契约下 4 个子代理并行编码 → 静态检查 + 真实浏览器端到端测试 → 华为云 CodeArts 仓库协作(dev → main → v1.0.0)→ 云部署 + CSDN 博客发布。
五、原型设计
5.1 原型工具与 AI 协作方式
原型阶段使用墨刀(MoDao)原型工具完成 8 个高保真页面(首页总览、走势对比、论文库、数据导入、研究方向、论文详情、阅读中心、关于),统一深色科技风格:深蓝底 #070c17、青色渐变主按钮、卡片式面板。与 AI 的协作方式为:我先用 AI 生成页面结构与配色草案,在墨刀中完成布局与交互稿,再让 AI 通读导出的 HTML 原型、输出「页面功能清单 + 缺陷清单」,作为编码阶段的输入;编码完成后又反过来以原型为基准做逐页视觉对照验收。
![原型首页]

![原型走势对比页]

5.2 界面与需求一致性
成品页面布局、组件样式与交互节奏与原型一一对应(详见 6.2 对照表)。原型是「mock 数据 + 假交互」的设计稿,编码阶段把每处假交互替换为真实数据流:虚标统计改实时口径、假爬取改三级真实通道、假 Excel 解析改真 CSV/JSON 解析、图谱点击改真实查询联动。
5.3 交互逻辑(跳转 / 弹窗 / 查询联动)
- 跳转:全站 7 处导航 + 每篇论文详情页 + 关键词/方向/作者三向跳转(如
papers.html?kw=Diffusion、paper-detail.html?id=P034、topics.html?topic=…),URL 参数驱动(含?edit=自动打开编辑弹窗)。 - 弹窗:论文新增/编辑、删除确认、批量删除、联网搜索四类模态,全部带校验与空态。
- 查询联动:关键词图谱点击节点 → 右侧论文面板实时更新;走势动图播放 → 主图 markLine、动态排行、会议对比条、年份滑块四方联动;阅读中心范围切换 → KPI、图表、标签云同步聚合。
- 数据流转梳理:借助 AI 画出「爬取通道 → 数据层 → 页面渲染」的数据流转图,逐页核对每条链路(详见 6.1)。
六、设计实现过程(功能结构图与系统设计)
6.1 功能结构图
CV Insight 顶会热词统计平台
├── 数据来源层
│ ├── 种子数据(82 篇真实论文,data.js)
│ ├── 在线爬取(Semantic Scholar → Crossref → 演示回退,crawler.js)
│ └── 批量导入(JSON / CSV / 多行文本,parseBatch)
├── 数据持久层(db.js,localStorage)
│ ├── 论文库:增 / 删 / 改 / 查(6 种检索 + 筛选 + 排序 + 分页)
│ ├── 个人数据:收藏 / 阅读状态 / 标签 / 笔记
│ ├── 爬取历史(最近 30 条)
│ └── 实时统计(stats():总数 / 会议 / 方向 / 年份 / 平均引用)
├── 可视化分析层(ECharts 5)
│ ├── Top 10 方向排行 + 会议分布环形图
│ ├── 关键词力导向图谱 + 标签云(点击联动论文)
│ ├── 多年 × 三会议走势对比动图(播放 / 滑块 / 动态排行)
│ └── 年度热词演变 Bar Race
└── 页面表现层(8 个 HTML,统一导航 / 页脚 / toast 组件)
├── index 首页总览 ├── trends 走势对比
├── papers 论文库 ├── import 爬取导入
├── topics 研究方向 ├── paper-detail 论文详情
├── library 阅读中心 └── about 关于 / NABCD
6.2 系统设计说明
共享数据层挂载在全局命名空间 CVI 下,按职责分为 data / db / crawler / charts / components / util 六个模块;页面层只做「读数据 → 渲染 → 绑定事件」,不复制数据。原型 6 页重复内联 mock 数据的缺陷被彻底消除:改一处种子,全站生效。
原型与成品对照:
| 原型页 | 成品页 | 关键变化 |
|---|---|---|
| home.html | index.html | 虚标「32,486 篇」改实时口径;图谱点击改真实数据查询 |
| trends.html | trends.html | 保留动图思路,新增 ICCV/ECCV 奇偶年处理与年度热词 Bar Race |
| papers.html | papers.html | 联网搜索升级为「就地弹出可导入结果」 |
| import.html | import.html | 假爬取(hashCode 合成数据)改三级真实通道;假 Excel 解析改真 CSV/JSON |
| library.html | library.html | 修复「最近更新」排序失效;图表按当前范围实时聚合 |
创新性与合理性:① 三级爬取通道 + 来源徽标 = 演示不中断且数据可溯源;② 「实时口径 / 演示口径」二分标注 = 统计数字全部可自圆其说;③ 按真实举办周期处理缺失年份 = 走势图符合顶会实际规律;④ 纯前端零 CDN = 离线环境也能完整演示。
七、代码说明(关键代码约 300 行)
7.1 三级爬取通道(功能 1 核心,crawler.js)
function searchOnline(query) {
if (!query || !query.trim()) return Promise.resolve({ source: '', items: [], mode: 'online' });
var fallback = function () {
return demoSearch(query.trim()).then(function (r) { r.mode = 'demo'; return r; });
};
return s2Search(query.trim())
.catch(function () {
return crossrefSearch(query.trim())
.catch(fallback);
})
.then(function (r) {
// 演示回退结果已由 fallback() 标记 mode='demo',此处不得覆盖
if (r.mode !== 'demo') r.mode = 'online';
if (!r.items.length) return fallback();
return r;
})
.catch(fallback);
}
思路:用 Promise 链把三个通道串成一条降级链路——主通道失败抛错进 catch 换次通道,次通道再失败进演示池;返回对象携带 mode 字段,界面据此渲染「Semantic Scholar API / Crossref API / 演示数据(离线回退)」三种来源徽标。此处曾有一个真实缺陷:外层 .then 无条件把 mode 覆盖成 online,导致演示回退时徽标与入库 source 矛盾,由两个并行开发的子代理同时发现,修复为「仅当未被标记 demo 时才设为 online」。
7.2 关键词提取与方向推断(crawler.js)
function extractKeywords(text) {
text = String(text || '');
var lower = text.toLowerCase();
var hit = [];
KW_LIST.forEach(function (k) {
if (lower.indexOf(k) >= 0 && hit.indexOf(k) < 0) hit.push(k);
});
if (hit.length) {
var canon = hit.map(function (k) {
// 还原词典中的原始写法(保持大小写/中文一致)
var orig = k;
Object.keys(KW_TOPIC).forEach(function (key) {
if (key.toLowerCase() === k && key.length >= orig.length) orig = key;
});
return orig;
});
return { keywords: canon.slice(0, 4), topic: inferTopic(canon) };
}
var tokens = text.match(/[A-Za-z][A-Za-z-]{3,}/g) || [];
var freq = {};
tokens.forEach(function (t) {
t = t.toLowerCase();
if (STOPWORDS.has(t)) return;
freq[t] = (freq[t] || 0) + 1;
});
var top = Object.keys(freq).sort(function (a, b) { return freq[b] - freq[a]; }).slice(0, 3);
return { keywords: top.map(function (t) { return t[0].toUpperCase() + t.slice(1); }), topic: '' };
}
思路:词典(十大方向关键词 + 种子关键词,共数百词条)优先——命中即作为关键词,并按「关键词 → 方向」映射投票推断研究方向;无命中时退化为英文词频提取(过滤停用词)。测试中发现 "Attention Is All You Need" 会提取出无意义的 "Need",遂扩充停用词表;Crossref 摘要的 HTML 实体(<p>)也由新增的 decodeEntities() 统一解码。
7.3 库内实时统计(功能 2/3 数据底座,db.js)
function all() {
var s = load();
var list = CVI.data.SEED_PAPERS.concat(s.user || []);
return list
.filter(function (p) { return (s.deleted || []).indexOf(p.id) < 0; })
.map(function (p) { return Object.assign({}, p, (s.overrides || {})[p.id] || {}); });
}
function stats() {
var list = all();
var byVenue = { CVPR: 0, ICCV: 0, ECCV: 0 };
var byTopic = {};
var byYear = {};
var kwCount = {};
var cites = 0;
list.forEach(function (p) {
if (byVenue[p.venue] != null) byVenue[p.venue]++;
byTopic[p.topic] = (byTopic[p.topic] || 0) + 1;
byYear[p.year] = (byYear[p.year] || 0) + 1;
cites += Number(p.citations) || 0;
(p.keywords || []).forEach(function (k) { kwCount[k] = (kwCount[k] || 0) + 1; });
});
return {
total: list.length,
byVenue: byVenue,
byTopic: byTopic,
byYear: byYear,
keywords: Object.keys(kwCount).length,
avgCitations: list.length ? Math.round(cites / list.length) : 0
};
}
思路:种子数据只读,用户操作全部落 localStorage(新增进 user、删除进 deleted、编辑进 overrides),all() 合并出「当前有效论文」;stats() 每次从这张实时列表聚合,首页 KPI、论文库统计条、关于页图表共用同一数据源——这是「杜绝原型数字虚标」的工程保证。
7.4 六种检索(功能 2,db.js)
function search(opts) {
opts = opts || {};
var q = (opts.q || '').trim().toLowerCase();
var type = opts.type || 'all';
var list = all();
if (opts.venue) list = list.filter(function (p) { return p.venue === opts.venue; });
if (opts.topic) list = list.filter(function (p) { return p.topic === opts.topic; });
if (opts.year) list = list.filter(function (p) { return String(p.year) === String(opts.year); });
if (opts.favOnly) list = list.filter(function (p) { return isFav(p.id); });
if (q) {
list = list.filter(function (p) {
var title = p.title.toLowerCase();
var authors = (p.authors || []).join(' ').toLowerCase();
var kws = (p.keywords || []).join(' ').toLowerCase();
var topic = (p.topic || '').toLowerCase();
var ab = (p.abstract || '').toLowerCase();
switch (type) {
case 'title-exact': return title === q;
case 'title': return title.indexOf(q) >= 0;
case 'id': return p.id.toLowerCase().indexOf(q) >= 0;
case 'author': return authors.indexOf(q) >= 0;
case 'keyword': return kws.indexOf(q) >= 0;
default: return title.indexOf(q) >= 0 || authors.indexOf(q) >= 0 ||
kws.indexOf(q) >= 0 || topic.indexOf(q) >= 0 || ab.indexOf(q) >= 0 || p.id.toLowerCase().indexOf(q) >= 0;
}
});
}
return list.slice().sort(function (a, b) {
return (b.year - a.year) || ((b.citations || 0) - (a.citations || 0));
});
}
思路:先做会议/方向/年份/收藏的精确过滤,再做检索类型的文本匹配(标题精确用全等、其余用包含),最后统一按年份降序、引用降序返回——论文库的全部查询入口(表格搜索、关键词跳转、作者跳转、阅读中心过滤)都收敛到这一个函数。
7.5 走势动图(功能 5,trends.html)
function trendValue(name, venue, yearIdx) {
const t = trendOf(name);
if (!t) return null;
const year = YEARS[yearIdx];
switch (venue) {
case 'CVPR': return t.shape[yearIdx]; // 每年都有
case 'ICCV': return (year % 2 === 1) ? Math.round(t.shape[yearIdx] * 0.88) : null;
case 'ECCV': return (year % 2 === 0) ? Math.round(t.shape[yearIdx] * 0.92) : null;
default: return t.shape[yearIdx]; // 全部会议
}
}
function setYear(i) {
state.yearIdx = CVI.util.clamp(i, 0, YEARS.length - 1);
document.getElementById('yearRange').value = state.yearIdx;
document.getElementById('yearLabel').textContent = YEARS[state.yearIdx];
renderTrend();
renderRank();
renderVenueBars();
}
/** 播放 / 暂停主区动图(900ms 推进一年,0→8 循环)。 */
function togglePlay() {
const icon = document.getElementById('playIcon');
const text = document.getElementById('playText');
if (state.timer) {
clearInterval(state.timer);
state.timer = null;
icon.setAttribute('icon', 'mdi:play');
text.textContent = '播放';
} else {
icon.setAttribute('icon', 'mdi:pause');
text.textContent = '暂停';
state.timer = setInterval(function () {
setYear((state.yearIdx + 1) % YEARS.length);
}, 900);
}
}
思路:trendValue 按会议真实举办周期输出数值(ICCV 只在奇数年有值、ECCV 只在偶数年,缺失返回 null 由 ECharts connectNulls 虚线连通)——这是全站最「懂顶会」的一处领域逻辑;togglePlay 用 setInterval(900ms) 推进年份,setYear 一次调用联动四个视图(主图 markLine、动态排行、会议对比条、滑块与年份标签),形成真正的「动图」而非静态 GIF。
7.6 关键词图谱(功能 4,index.html)
function buildKwGraph() {
const topicIndex = {};
CVI.data.TOPICS.forEach(function (t, i) { topicIndex[t.name] = i; });
const categories = CVI.data.TOPICS.map(function (t) { return { name: t.name, itemStyle: { color: t.color } }; });
// 关键词节点
const nodes = CVI.data.KEYWORDS.map(function (k) {
return {
name: k.kw,
value: k.weight,
symbolSize: 12 + k.weight / 4.2,
category: topicIndex[k.topic] != null ? topicIndex[k.topic] : 0,
label: { show: k.weight >= 50, fontSize: k.weight >= 80 ? 12 : 11 }
};
});
// 关键词 → 所属方向 连边
const links = CVI.data.KEYWORDS.map(function (k) {
return { source: k.kw, target: k.topic, lineStyle: { opacity: 0.22 } };
});
// 方向节点(大节点)
CVI.data.TOPICS.forEach(function (t) {
nodes.push({
name: t.name, value: 120, symbolSize: 30, category: topicIndex[t.name],
label: { show: true, fontSize: 11.5 }, itemStyle: { color: t.color, opacity: 0.95 }
});
});
kwChart = echarts.init(document.getElementById('kwGraph'));
kwChart.setOption({
backgroundColor: 'transparent',
tooltip: Object.assign({
formatter: function (p) {
if (p.dataType === 'edge') return '';
if (p.data.value === 120) return '<b>' + esc(p.name) + '</b><br/>点击查看该方向论文';
return '<b>' + esc(p.name) + '</b><br/>热度权重:' + p.data.value + '<br/>点击查看相关论文';
}
}, CVI.charts.TIP),
legend: [{
bottom: 0, itemWidth: 9, itemHeight: 9, textStyle: { color: '#94a3b8', fontSize: 11 },
data: CVI.data.TOPICS.map(function (t) { return t.name; })
}],
series: [{
type: 'graph',
layout: 'force',
roam: true,
draggable: true,
categories: categories,
force: { repulsion: 210, edgeLength: [38, 105], gravity: 0.09 },
label: { color: '#cbd5e1', position: 'right' },
lineStyle: { color: 'source', curveness: 0.12, opacity: 0.3, width: 1 },
emphasis: { focus: 'adjacency', label: { color: '#fff', fontSize: 13 } },
data: nodes,
links: links
}]
});
kwChart.on('click', function (params) {
// 点击关键词 → renderKwPanel 查询相关论文;点击方向 → 展示方向论文并给出跳转
// (点击处理代码略,逻辑为:CVI.db.byKeyword(kw) / byTopic(topic) 取前 8 篇渲染右侧面板)
});
}
思路:20 个关键词小节点 + 10 个方向大节点,节点大小按权重、颜色按方向分类,力导向参数(斥力 210、边长 38–105、重力 0.09)经多次调试达到稳定不重叠的布局;点击事件是功能 4 的灵魂——关键词走 db.byKeyword()、方向走 db.byTopic(),右侧面板实时联动,标签云视图提供第二入口。
7.7 批量导入(功能 1,import.html)
function runImport() {
const ok = batchRows.filter(r => r.status === 'ok');
if (!ok.length) { toast('没有可导入的记录', 'error'); return; }
const papers = ok.map(r => {
const kw = CVI.crawler.extractKeywords(r.title); // 用标题补全关键词与方向
return {
// 不预计算 id:交由 CVI.db.addMany 按序分配,避免批量重复编号
title: r.title,
authors: (r.authors && r.authors.length) ? r.authors : ['未知作者'],
venue: r.venue,
year: r.year,
topic: kw.topic || CVI.data.TOPICS[0].name,
keywords: kw.keywords.length ? kw.keywords : ['未标注'],
abstract: '(由批量导入写入,摘要可在论文库管理中补充)',
citations: 0,
url: r.url,
source: 'import'
};
});
const n = CVI.db.addMany(papers);
CVI.db.logCrawl({ type: 'batch', query: MODE_LABEL[batchMode] || '批量导入', source: '手动导入', count: n });
toast('成功导入 ' + n + ' 篇', 'success');
batchDone = n;
batchRows = []; // 清空预览
$('batchText').value = '';
renderBatch();
}
思路:预览表格逐行校验(标题空 / 会议非法 / 年份越界 / 与库内重复)后,只导入状态为 ok 的行,并自动用标题补全关键词与方向。注释里那句话是一个真实 bug 的墓碑:初版在这里预计算 CVI.db.nextId(),导致同批次论文拿到同一编号(两篇都是 P084),浏览器实测抓到后改为由 addMany 按序分配。
7.8 联网检索一键导入(功能 2 加分项,papers.html)
function importDirect(idx) {
const item = (state.onlineItems || [])[idx];
if (!item) return;
const title = String(item.title || '').trim();
if (!title) {
CVI.util.toast('该结果缺少标题,无法导入', 'error');
return;
}
// 重复导入保护:库内已有同名论文时不重复入库
const dup = CVI.db.all().find(p => p.title.toLowerCase() === title.toLowerCase());
if (dup) {
CVI.util.toast('该论文已存在于论文库(' + dup.id + '),未重复导入', 'error');
return;
}
const ex = CVI.crawler.extractKeywords(title + ' ' + (item.abstract || ''));
const added = CVI.db.add({
title: title,
authors: (item.authors && item.authors.length) ? item.authors.slice() : ['未知作者'],
venue: item.venue || '',
year: item.year || new Date().getFullYear(),
topic: ex.topic || '',
keywords: ex.keywords.length ? ex.keywords : ['未标注'],
abstract: (item.abstract || '').trim() || '(原文未提供摘要)',
citations: 0,
url: item.url || '',
source: state.onlineMode === 'demo' ? 'demo' : 'crawl'
});
CVI.util.toast('已导入「' + added.title.slice(0, 24) + '」· ' + added.id, 'success');
closeOnline();
render();
}
思路:本地搜索无结果时空态提供「联网搜索」按钮,弹窗展示爬取通道返回的结果列表(带来源徽标),每条支持「导入并编辑」与「直接导入」;这里做了两层防御——缺标题拒绝导入、库内同名拒绝重复导入,且导入记录按在线/演示正确标注 source,保证全平台数据可溯源。
八、成品展示
部署访问链接(云服务器公网 IP 或域名):http://124.71.233.50/
- 首页 · 热门方向总览与关键词图谱(功能 3、4)

- 热度走势对比动图 · 播放中(功能 5)

- 走势对比 · ICCV 会议维度(奇数年举办,偶数年按缺失处理)

- 论文库管理 · 默认视图(功能 2)

- 论文库 · 标题搜索(6 种检索之一)

- 单篇爬取 · 真实 Crossref API 结果表单(功能 1)

- 研究方向详情页(实时收录 + 演示走势 + 会议构成)

- 论文详情 · 相似推荐与阅读管理

- 阅读中心 · 收藏 / 状态 / 标签 / 笔记(附加分)

- 关于页 · NABCD 模型区(附加分「了解更多」)

- 走势页 · 年度热词演变 Bar Race 区(附加分)

- 数据导入页默认视图(单篇爬取 + 批量导入 + 爬取历史)

九、人机讨论(AI 结对协作记录)
与 AI 结对全程的记录(6 个案例完整版:提示词原文、AI 输出摘要、修改迭代、采纳/拒绝理由,见仓库 docs/AI-collab.md)。以下按作业要求给出 3 个代表性案例 + 可解释性声明 + 反思。
案例 1:让 AI 通读原型,输出结构化功能清单与缺陷清单
- 提示词(节选):「请仔细阅读 F:\下载\Bs0OUK4yCwns7Tnm8JS2Ne 文件夹中的 7 个 HTML 文件……为每个页面报告:核心功能、JS 逻辑/函数清单、是否重复内联相同数据、外部 CDN 引用清单、原型中明显的缺陷或『仅演示』占位内容。」
- AI 输出摘要:约 1500 字结构化报告,逐页列出函数清单,并指出 6 项缺陷:6 页重复内联 SEED 数据、统计全为 mock、4 篇虚构论文(P022/P027/P028/P030)、假 Excel 解析、placeholder 占位图、about 页「32,486 篇」与 30 条种子矛盾。
- 修改理由 / 采纳:报告直接成为重构方案的事实基础——共享数据层、真实论文替换、统计口径二分三条设计决策均源于此。全部采纳。
案例 2:SPEC 契约 + 4 个并行子代理开发 8 个页面
- 提示词(节选,发给 4 个并行代理):「完整阅读 SPEC.md(页面骨架、可用 API、图标白名单、视觉规范、数据口径)……视觉与布局必须与原型高度一致……严禁 CDN 引用、严禁内联种子数据、严禁硬编码与库内矛盾的统计数字。」
- AI 输出摘要:8 个页面全部交付并附自检报告;两个互不通信的代理同时报告了共享层 crawler.js 的同一缺陷(演示回退时 mode 被覆盖为 online)。
- 修改理由 / 采纳:并行把 8 页工作量压缩到单页时间;契约保证四个代理产出一致的接口风格。采纳并行与契约;拒绝代理的 DOM 桩测试结论——「31 项测试全部通过」的页面在真浏览器里被实测出重复编号 bug(见案例 3),改由主会话驱动真实浏览器逐项复测。
案例 3:真浏览器实测抓到「批量导入重复编号」bug
- 提示词(测试操作):填入示例数据 → 解析预览 → 导入 → 观察;随后「grep nextId import.html」定位。
- AI 输出摘要:观察到两篇导入论文同编号 P084;定位为
runImport()在 map 里为每篇论文预先调用nextId(),而addMany只在无 id 时才分配——预计算导致同批次同一编号。 - 修改理由 / 采纳:删除两处预计算,统一由数据层顺序分配;修复后浏览器复测通过(P083/P084 唯一)。这是「人类描述场景 → AI 定位缺陷 → 人类拍板 → AI 修复 + 回归」的完整闭环。采纳。
可解释性声明:本项目全部代码与文档均由 AI 在人类明确指示下生成或修改,人类负责需求决策、数据真实性把关与最终验收;AI 生成内容未经过滤地保留在 AI-collab.md 中可查。文中引用量为近似值、走势与权重为演示口径,均已在界面标注。
反思评价:AI 结对的最大收益是「并行 + 契约」——SPEC 让互不通信的代理产出可以合龙;最大的风险是「自信的自检」——AI 说全绿不等于真的全绿,端到端验收必须由人把关(详见第十章)。
10、心路历程与对 AI 伙伴的评价
10.1 心路历程
- 最难的决策:原型声称「收录 32,486 篇」却只有 30 条种子、还混着 4 篇虚构论文。与其把假数字做得更漂亮,不如把诚实做成本文的卖点——最终确立「实时口径 / 演示口径」二分标注原则,每一处统计都能自圆其说。
- 最惊喜的时刻:浏览器实测中,联网搜索真的打到了 Crossref API 并返回了真实论文数据——三级回退通道在无人干预下自动完成「主通道失败 → 次通道成功」的切换。
- 最深刻的教训:两个页面代理的报告都写着「31 项测试全部通过」,真浏览器里却冒出一个重复编号 bug。AI 的自信需要人类的验收来兜底。
10.2 结合《构建之法》第 4 章:人机结对 vs 传统结对
《构建之法》第 4 章讲两人结对编程:一人写、一人看,实时评审、互相监督。人机结对与之相比:
- 相同点:都存在「执行者 + 评审者」的双重视角;都需要明确分工与可复核的产出;低质量的协作都会产生返工成本。
- 不同点:传统结对靠的是即时讨论与情感激励,人机结对靠的是契约——我把「页面骨架、可用 API、图标白名单、数据口径」写成 SPEC.md,等于把结对协议文档化,四个 AI「伙伴」并行工作也不会互相踩踏;但 AI 不会像人类搭档那样质疑需求本身,它会忠实执行一个错误的前提(比如原型里的假数据),质疑与纠偏的责任完全落在人这一侧。
- AI 的优势:速度快(8 页并行 30 分钟)、不疲劳、能同时保持多份上下文、机械检查(图标白名单 / 链接存在性 / 语法)零遗漏。
- AI 的局限:自检结论不可尽信(DOM 桩测试全绿 ≠ 真浏览器可用);会「自信地」产出虚构内容(原型里的虚构论文就是前车之鉴);无法理解「课堂演示不能断网」这类真实世界约束——需要人把约束翻译成三级回退通道这种可实现的需求。
10.3 对 AI 伙伴的评价
这位 AI 伙伴像一位执行力极强、但需要明确契约的搭档:给它一份清楚的 SPEC,它能并行交付 8 个高质量页面并互相发现对方的 bug;它诚实(两个代理不约而同上报同一缺陷而非掩盖),也勤勉(浏览器测试一步步真实点击而非假装通过)。但它同样会「把假的说得像真的」,所以我的评价是:值得长期结对,前提是每一次信任都必须经过人的验收——这也正是结对编程这门课想教给我们的东西。
10.4 下一步
接入 DBLP 全量快照做真实走势统计、增加论文相似度网络图、支持导出 BibTeX,让平台从「作业」走向「工具」。
相关推荐
人工智能大报告+作业练习.zip
机器学习训练AI游戏小鸟越过障碍,可达到150分左右甚至更高,里面还含有一些常见的人工智能专业的题目,更好的是里面的报告内容非常详细还有学习心得等,都是作者亲自做的,为的就是给师弟师妹啊。
人工智能大作业.zip
涉及知识表示与推理,机器学习,自然语言处理(词云、分词)的一个五子棋对战系统。采用java语言编写。中有完整代码,讲解视频,项目报告,一应俱全。
北京交通大学-软件工程专硕-曾立刚-《AI人工智能开发框架》小作业
2021年秋季学期-北京交通大学软件工程专硕《AI开发框架》作业,总共7个小作业,曾立刚老师要求选4-5个写,待课程结束后统一上交
Python_aider是在您的终端中的AI结对编程.zip
Python_aider是在您的终端中的AI结对编程
人工智能(AI)学习:从Python到AI编程
由于Python具有強大的延展性,可以很容易的与別人分享自己所写的程序代码,因此也很容易汇入各式各样別人的程序代码。许多可以分享的案例,包括Python本身所提供的标准案例,通称为模组(Module)或程式庫(Library)。除了Python本身的标准程序库之外,还有許多其他人(又称第三方)分享的程序库。这些分享的模组都成为Python中非常重要的東西,通称为Python的扩充套件。



