ARTICLE DETAIL

建站实战干货

来自一线的建站与推广经验沉淀,每一条都经过真实交付验证。

基于Qwen-Plus大模型与知识图谱的智能出题系统设计与实现

2026/8/30 15:55:08 拓冰建站 浏览量
基于Qwen-Plus大模型与知识图谱的智能出题系统设计与实现 这次我们要做的不是传统题库管理系统而是一个真正接通真实大模型能力的“智能生成题目系统”。核心思路很直接后端调用阿里云百炼的 Qwen-Plus 大模型接口根据指定知识点、题型、难度自动生成题目再用 Neo4j 把“题目—知识点—学生—错题”织成知识图谱最后基于错题记录做知识点关联分析给学生输出复习建议。这三个能力叠在一起正好覆盖“AI 应用落地 数据结构设计 业务逻辑闭环”三个毕业设计高频考察点拿来答辩的完整度和演示效果都会比普通 CRUD 系统高一个档次。这篇文章会把整个系统的可落地路径拆开讲从技术选型、环境准备、Qwen-Plus 接入、知识图谱构建、错题分析到 API 批量出题、性能观察和问题排查。我们不搞花哨概念重点说清楚每一步怎么实现、验证时看什么指标、踩坑了怎么处理。本文配套的源码包已经整理好按文末说明就可以拿到。1. 核心能力速览先把系统的能力边界和硬性要求放出来方便你快速判断这个方向适不适合自己。能力项说明系统类型智能生成题目系统面向毕业设计/课程设计核心模型Qwen-Plus通过阿里云百炼 API 接入主要功能AI 自动出题、题目知识点关联、知识图谱构建与可视化、错题知识点分析、薄弱环节复习建议知识图谱Neo4j 图数据库存储知识点、题目、学生、错题记录等实体和关系后端框架推荐 FastAPI 或 Flask按实际源码结构选择前端方案Vue 或纯 HTML 接口请求可根据答辩演示环境灵活选择硬件要求低无需本地 GPU大模型能力由云端 API 提供启动方式Python 环境安装依赖配置 API Key 后启动服务接口能力提供 HTTP 接口支持题目生成、知识点查询、错题分析结果查询批量任务支持按知识点列表批量出题需增加延时与重试逻辑适合场景毕设答辩演示、题库系统增强、在线教育辅助工具原型从材料看这个项目最关键的优势是大模型出题能直接体现“AI 能力”知识图谱能体现“数据关联设计”错题分析能体现“业务闭环”。三个功能点随便选一个展开都能撑起答辩问答环节。2. 系统总体架构在写代码之前先把架构理清楚。这个系统本质上由四层组成每一层都有独立的职责前端页面Vue/HTML ↓ HTTP 请求 后端服务FastAPI/Flask ├── 出题服务模块 → 调用 Qwen-Plus API → 返回结构化题目 JSON ├── 知识图谱模块 → Neo4j 图数据库题目与知识点关系维护 └── 错题分析模块 → 读取错题记录 → 关联知识点 → 生成复习建议出题服务模块是入口。用户在前端输入“知识点 题型 难度 题目数量”后端组装成提示词Prompt调用 Qwen-Plus 模型接口拿到 JSON 格式的题目结果再写入数据库并返回给前端。知识图谱模块负责把题目和知识点之间建立关系。比如一道数学题“求一元二次方程 x²-5x60 的解”它对应的知识点节点是“一元二次方程”二者通过[:TESTS]关系连接。多个题目之间可以通过前置知识点形成依赖关系后续做复习路径推荐时很有用。错题分析模块负责读取学生在答题记录中的错误数据提取错题涉及的知识点再结合知识图谱中的前置依赖关系定位学生的薄弱环节生成“巩固 A 知识点后再练 B 知识点”的建议。三层逻辑串起来后演示时就可以走通一个完整业务场景学生做一套题 → 系统记录错题 → 错题分析模块给出知识点薄弱项 → 系统基于薄弱知识点调用大模型生成针对性练习题。3. 适用场景与使用边界3.1 适合谁用这个系统定位很明确适合三类人一是毕业设计方向是 AI 应用开发、智慧教育、在线题库的同学。把 Qwen-Plus 接入到出题场景里论文里可以写“基于大模型的智能出题方案研究”工作量和技术含量比传统题库高不少。二是需要做课程设计或创新实践项目的学生。系统不需要本地 GPU不需要复杂的模型部署只要一个 API Key 就能跑通落地成本非常低。三是想快速做一个教育类项目原型的开发者。这个项目天然包含数据库设计、接口设计、第三方 API 集成、业务逻辑闭环可以作为一个微缩版的中台系统来学习。3.2 不适合什么场景如果要做的是大规模在线考试系统追求生产级高并发这个项目的架构还需要加强。大模型出题有响应延迟不可能替代传统人工出题库也不适合作为考试系统唯一题目来源。如果打算做本地私有化部署的教育平台完全不使用云 API那 Qwen-Plus 这种方式就不合适需要改成本地开源模型方案但这会引入 GPU 硬件成本和部署复杂度的提升。3.3 使用边界与合规提醒AI 生成题目内容的准确性无法保证正式使用前必须人工审核避免出现在知识讲解中误导学生。涉及学生姓名、学号、答题记录等数据时要做脱敏处理接口层加权限校验不能直接暴露在内网外。题目素材如果有版权来源不要原样灌给模型去生成变体题。论文和答辩材料中要明确说明使用了大模型 API 服务符合学校对第三方 AI 工具使用的规定。4. 环境准备与前置条件4.1 运行环境清单建议按以下清单准备环境版本只给兼容范围具体以能跑通为准环境项推荐配置说明操作系统Windows 10/11、Ubuntu 20.04开发演示推荐 Windows服务器部署推荐 LinuxPython3.9所有后端逻辑都基于 PythonNode.js16仅前端构建时需要如果使用纯 HTML 可跳过Neo4j4.4 / 5.x Community图数据库用于知识图谱存储阿里云百炼账号开通 DashScope API用于获取 Qwen-Plus 调用权限集成开发环境PyCharm 或 VS Code按个人习惯选择4.2 项目目录结构规划目录结构建议这样规划源码包也会按这个思路整理smart-quiz-system/ ├── backend/ │ ├── app.py # FastAPI 入口 │ ├── config.py # 读取环境变量管理 API Key │ ├── services/ │ │ ├── llm_service.py # Qwen-Plus 出题服务 │ │ ├── graph_service.py # Neo4j 知识图谱服务 │ │ └── wrong_analysis.py # 错题分析服务 │ ├── models/ │ │ └── schemas.py # 数据模型定义 │ └── requirements.txt ├── frontend/ │ └── index.html # 简单演示页面 ├── data/ │ └── questions.json # 出题结果样例 ├── .env.example # API Key 环境变量模板 └── README.md4.3 依赖安装在项目目录下创建虚拟环境并安装依赖。这里给出一个通用依赖列表实际以源码包的requirements.txt为准python -m venv venv # Windows venv\Scripts\activate # Linux/Mac source venv/bin/activate pip install fastapi uvicorn openai neo4j python-dotenv requests说明openai库用来调用阿里云百炼的 OpenAI 兼容模式接口neo4j是 Neo4j 官方 Python 驱动python-dotenv用来读取.env中的 API Key。如果前端使用 Vue再单独在frontend目录执行npm install。5. Qwen-Plus 大模型出题接入5.1 获取 API Key这一步需要先开通阿里云百炼服务并创建 API Key。进入百炼控制台后在 API-KEY 管理页面创建密钥保存到本地.env文件DASHSCOPE_API_KEYsk-你的密钥 BASE_URLhttps://dashscope.aliyuncs.com/compatible-mode/v1 MODEL_NAMEqwen-plus.env文件不要提交到 Git源码包中只放.env.example模板。5.2 调用 Qwen-Plus 生成题目接入方式使用 OpenAI 兼容接口底层是 HTTP 请求用openai这个 Python SDK 就能直接对接。下面这段是出题服务的核心代码注意替换你自己的 API Keyimport os import json from openai import OpenAI from dotenv import load_dotenv load_dotenv() client OpenAI( api_keyos.getenv(DASHSCOPE_API_KEY), base_urlos.getenv(BASE_URL), ) def generate_questions( knowledge_point: str, subject: str 数学, difficulty: str 中等, question_type: str 选择题, num: int 3 ) - list: system_prompt ( 你是一名资深学科出题老师擅长根据知识点命制高质量题目。 题目必须严谨、无歧义难度符合要求。 请返回 JSON 数组每个题目包含字段 type, difficulty, knowledge_point, stem, options, answer, analysis ) user_prompt ( f请为【{subject}】学科命制 {num} 道题目。\n f知识点{knowledge_point}\n f题型{question_type}\n f难度{difficulty}\n 要求答案准确解析简明并且适合学生练习。 ) resp client.chat.completions.create( modelos.getenv(MODEL_NAME, qwen-plus), messages[ {role: system, content: system_prompt}, {role: user, content: user_prompt}, ], temperature0.7, # 如果模型服务支持结构化输出可以启用下面参数 # response_format{type: json_object}, ) content resp.choices[0].message.content return json.loads(content)这段代码的关键点有两个一是提示词设计。系统提示词一定要说明“返回 JSON 数组”和“包含字段”不然模型会返回一段带解释的自然语言文本后续解析非常麻烦。本文给的字段是type, difficulty, knowledge_point, stem, options, answer, analysis在源码里你可以根据自己的需求调整。二是温度参数。出题场景建议设 0.7 左右太高容易输出不稳定内容太低会导致同质化严重。如果你要连续生成多套题目可以把温度在 0.6 到 0.9 之间随机变化。5.3 出题结果 JSON 示例Qwen-Plus 正常返回后解析出的题目结构类似下面这样[ { type: 选择题, difficulty: 中等, knowledge_point: 一元二次方程, stem: 一元二次方程 x^2 - 5x 6 0 的两个根是, options: [2和3, -2和-3, 1和6, -1和-6], answer: A, analysis: 对方程左侧因式分解得 (x-2)(x-3)0所以 x2 或 x3。 } ]拿到结构化题目后后端可以直接写入 MySQL 或 Neo4j也可以先存成 JSON 文件做本地缓存答辩演示时即使 API 临时不可用也能展示效果。这个思路非常建议保留先跑通 API再落地持久化最后接前端。6. 知识图谱构建与题目关联6.1 图谱实体与关系设计知识图谱在毕设里是加分项核心是把数据关系可视化出来让评委一眼看出你的数据结构是“图”而不是普通表。这里给出常用实体和关系设计实体 知识点KnowledgePointname、subject、grade 题目Questionqid、content、type、difficulty、answer 学生Studentsid、name、class_name 错题记录WrongRecordwid、wrong_time、wrong_answer 关系 (Question)-[:TESTS]-(KnowledgePoint) 题目考查某知识点 (Student)-[:ANSWERED]-(Question) 学生回答了某题目 (Student)-[:WRONG]-(Question) 学生做错了某题目 (KnowledgePoint)-[:PREREQUISITE_OF]-(KnowledgePoint) 知识点前置依赖6.2 Neo4j 数据写入示例在 Neo4j 中创建节点和关系可以直接用 Cypher 语句。下面给出一个最小可运行示例实际表结构字段可以按源码调整CREATE (k1:KnowledgePoint {name: 一元二次方程, subject: 数学, grade: 初三}); CREATE (k2:KnowledgePoint {name: 因式分解, subject: 数学, grade: 初二}); CREATE (q1:Question { qid: Q001, content: 一元二次方程 x^2 - 5x 6 0 的两个根是, type: 选择题, difficulty: 中等, answer: A }); CREATE (q1)-[:TESTS]-(k1); CREATE (k2)-[:PREREQUISITE_OF]-(k1);用 Python 的neo4j驱动执行 Cypher 时可以这样写from neo4j import GraphDatabase driver GraphDatabase.driver(bolt://localhost:7687, auth(neo4j, password)) def create_knowledge_point(name, subject, grade): with driver.session() as session: session.run( CREATE (k:KnowledgePoint {name: $name, subject: $subject, grade: $grade}), namename, subjectsubject, gradegrade )实际项目中最好把“创建节点”和“创建关系”封装成独立函数。每道题生成后先查一下对应知识点节点是否存在如果不存在就先创建避免重复节点。这里$name、$subject是参数化查询可以防止 Cypher 注入也方便复用。6.3 图谱可视化Neo4j Browser 自带可视化功能启动 Neo4j 后在浏览器打开http://localhost:7474执行MATCH (n)-[r]-(m) RETURN n, r, m LIMIT 100;就能看到图谱连线。答辩演示时直接投屏展示这个页面比贴 ER 图更有说服力。7. 错题分析功能实现7.1 分析逻辑错题分析的目的是从“学生答错的题”中找到“薄弱知识点”再给出下一轮练习建议。逻辑并不复杂1. 学生提交答案后保存答题记录如果答错则插入 WrongRecord。 2. 查询该错题关联的知识点节点。 3. 在知识图谱中查找该知识点的前置依赖知识点。 4. 汇总学生错题高频知识点生成复习建议。比如某位学生在“一元二次方程”的两道题上连续错误系统首先把“一元二次方程”标记为薄弱知识点然后在图谱中发现“因式分解”是它的前置知识点于是建议学生先复习“因式分解”再做“一元二次方程”的针对性题目。这种推荐逻辑在答辩时可以完整讲清楚。7.2 错题分析核心代码下面的代码演示了如何查询错题对应的知识点并分析薄弱环节。这是通用伪代码实际实现需要替换成源码包中的真实函数名def analyze_wrong_questions(student_id: str, driver): query MATCH (s:Student {sid: $student_id})-[:WRONG]-(q:Question)-[:TESTS]-(k:KnowledgePoint) RETURN k.name AS knowledge_point, count(q) AS wrong_count ORDER BY wrong_count DESC with driver.session() as session: result session.run(query, student_idstudent_id) weak_points [record[knowledge_point] for record in result] suggestions [] for point in weak_points: # 查找前置依赖知识点 dep_query MATCH (k:KnowledgePoint {name: $point})-[:PREREQUISITE_OF]-(pre:KnowledgePoint) RETURN pre.name AS prerequisite with driver.session() as session: deps session.run(dep_query, pointpoint) prerequisites [record[prerequisite] for record in deps] suggestions.append({weak_point: point, prerequisites: prerequisites}) return suggestions7.3 复习建议生成根据分析结果系统可以自动生成一句复习建议例如你在“一元二次方程”知识点上错误较多。 建议先巩固前置知识点“因式分解”再完成以下针对性练习。再把薄弱知识点列表传入第 5 节的generate_questions函数就能让 Qwen-Plus 针对薄弱点自动生成新题目完成“错题分析 → 薄弱点判定 → 定向出题”的闭环。这一步是整个系统的业务高光点答辩时建议现场演示。8. 接口 API 与批量出题设计8.1 FastAPI 接口示例后端使用 FastAPI 提供服务下面是一个简化的接口定义from fastapi import FastAPI from pydantic import BaseModel from services.llm_service import generate_questions from services.graph_service import save_question_to_graph app FastAPI() class GenerateRequest(BaseModel): knowledge_point: str subject: str 数学 difficulty: str 中等 question_type: str 选择题 num: int 3 app.post(/api/generate-questions) def api_generate_questions(req: GenerateRequest): questions generate_questions( knowledge_pointreq.knowledge_point, subjectreq.subject, difficultyreq.difficulty, question_typereq.question_type, numreq.num ) # 将题目写入知识图谱并返回结果 for q in questions: save_question_to_graph(q) return {code: 0, data: questions}启动服务uvicorn app:app --host 0.0.0.0 --port 80008.2 前端或第三方调用示例接口跑通后可以用 Python 的requests工具测试调用import requests url http://127.0.0.1:8000/api/generate-questions payload { knowledge_point: 等差数列, subject: 数学, difficulty: 中等, question_type: 填空题, num: 5 } resp requests.post(url, jsonpayload, timeout120) print(resp.json())如果是前端页面直接使用fetch请求同一地址即可。需要注意跨域问题前端开发时可让 FastAPI 加上CORSMiddleware允许本地访问。8.3 批量出题任务设计一次只出一个知识点演示效果有限。批量任务建议这样设计import time knowledge_points [一元二次方程, 等差数列, 三角函数, 平面向量, 导数] for index, kp in enumerate(knowledge_points): print(f正在生成第 {index 1} 个知识点{kp}) questions generate_questions(knowledge_pointkp, num3) for q in questions: save_question_to_graph(q) # 避免触发 API 访问频率限制 time.sleep(1)批量任务要注意三点每次调用之间加延时避免快速连续请求触发限流。单次生成数量不要过大建议每次 3 到 5 道题保证响应时间可控。记录日志某次调用失败后可以单独重试不影响整体任务。9. 性能观察与稳定性9.1 出题响应时间大模型出题的响应时间主要受三个因素影响题目数量、提示词长度、模型服务端排队情况。单题响应通常在 3 到 10 秒级别批量出题时前端页面要设计加载状态否则用户会以为系统卡死。建议在接口层设置超时时间比如 120 秒并在异常时返回明确提示而不是让请求一直挂起。源码中可以统一封装超时和重试逻辑提升答辩演示的稳定性。9.2 缓存与降级方案答辩环境存在不确定性比如校园网络波动或 API 临时不可用。建议设计一套降级方案把之前成功生成的题目持久化到本地 JSON 或数据库演示时如果 API 调用失败就从本地题库中读取缓存题目返回。def get_questions_with_cache(knowledge_point: str): # 1. 尝试调用大模型接口 # 2. 失败时读取本地缓存文件 # 3. 都没有时返回友好错误信息 pass这样做的好处是即使现场 API 测试失败系统仍然有数据可展示不影响答辩流程。9.3 Neo4j 查询性能知识图谱查询在本项目中的数据量级不会太大几百个节点、上千条关系的查询性能没有问题。需要注意避免在关系遍历时不加 LIMIT防止返回大量数据导致页面卡顿。10. 常见问题与排查方法问题现象可能原因排查方式解决方案API 返回 401 错误API Key 错误或未配置检查.env文件和环境变量重新生成 API Key确认前后没有多余空格接口响应超时模型服务排队或网络波动查看服务端日志确认请求是否发出增加超时时间设置重试机制使用缓存降级JSON 解析失败模型返回了非 JSON 内容打印原始返回内容强化 System Prompt要求只输出 JSON或使用结构化输出参数Neo4j 连接失败服务未启动或密码错误检查 Neo4j Browser 能否打开启动 Neo4j确认端口和账号密码前端页面无法访问后端跨域或端口不一致打开浏览器 F12 查看请求报错后端配置 CORS统一端口批量出题中途卡住单个知识点请求超时查看任务日志定位卡住点增加单请求异常捕获失败后跳过并记录日志题目内容重复温度参数太低查看生成记录提高 temperature或随机化 prompt 提示词题目解析不准确模型知识盲区人工抽检题目内容增加人工审核环节限定知识点范围11. 最佳实践与答辩演示建议11.1 开发阶段的工作习惯先不做完整界面优先跑通“Qwen-Plus 出题 → 返回 JSON → 写入 Neo4j → 查询结果”这一条主链路。建议准备一套最小测试数据比如 3 个知识点、5 道题、2 个学生、3 条错题记录确保整个流程能闭环。模型文件、输入素材、输出结果分目录管理。本文一致建议把出题结果先落到data/questions.json再决定是否写入数据库。调试阶段先看 JSON 数据减少数据库交互带来的干扰。11.2 答辩演示脚本建议演示时按以下顺序走打开系统首页输入一个具体知识点比如“一元二次方程”。点击生成题目展示 Qwen-Plus 返回结果和前端渲染效果。打开 Neo4j Browser执行MATCH (n)-[r]-(m) RETURN n, r, m展示知识图谱。选择一名学生进入错题分析页展示薄弱知识点和复习建议。点击“生成针对性练习”让大模型基于薄弱知识点再出题形成闭环。整个过程控制在 5 到 8 分钟重点展示“AI 出题”和“错题分析”两个亮点知识图谱作为数据关系佐证。11.3 合规与安全边界答辩前把所有演示数据改成虚拟学生姓名和脱敏数据不要使用真实学生隐私信息。AI 生成的题目答案需要人工复核不能直接作为正式考试成绩依据。论文中要写明大模型生成内容存在不确定性系统设计包含人工审核环节。这些都是评委容易追问的角度提前准备回答反而会成为加分项。12. 总结与下一步这个项目最值得尝试的点是把真实大模型 API 接进了一个业务闭环完整的系统中。你不用自己训练模型不需要买 GPU却能在答辩时展示出“AI 能力”这是性价比很高的毕设方向。最先应该验证的功能是让 Qwen-Plus 稳定返回指定格式的 JSON 题目推荐你第一步只测一个知识点、3 道题跑通后再扩展。最容易踩的坑有三个一是提示词设计不合理导致返回格式不稳定二是批量出题时没有做延时触发限流三是 API 临时不可用导致现场演示翻车。这三个问题在本文第 5、8、9 节都有对应方案建议开发时直接按这些思路实现。后续可以继续扩展的方向很多接入更多模型做题目多样性对比增加题目难度自适应推荐把错题分析做成可视化图表甚至加入语音读题能力。如果代码结构保持清晰这些功能都能稳步叠加。建议收藏备用源码整理好之后按前文说明获取先把主链路跑通再逐步完善细节。