
1) 【一句话结论】:竞赛题库的题目元数据(结构化,如内容、标签、难度)和用户权限数据(结构化,需强事务),以MySQL作为主要存储方案,通过分库分表、读写分离应对高并发;非结构化数据(如题目图片)存储在对象存储(如阿里云OSS),用户行为日志用MongoDB;全文检索用Elasticsearch,三者结合满足不同场景,其中MySQL因满足数据一致性、事务需求及扩展性设计,是核心存储。
2) 【原理/概念讲解】:
MySQL(关系型数据库):基于表结构,列有固定类型,数据以行存储,支持ACID事务(原子性、一致性、隔离性、持久性),类比企业财务账本,每一笔数据有明确字段(如题目ID、内容、标签),适合结构化数据,保证数据完整性和一致性。分库分表策略:按知识点或难度分库(如算法库、数据结构库),读写分离(主库写,从库读),应对高并发读写。
MongoDB(文档型NoSQL):以JSON文档为存储单位,字段灵活,无固定表结构,类似“文档集合”,适合半结构化或文档型数据(如题目解析、用户学习日志),水平扩展性好,但缺乏强事务支持(多文档事务仅支持部分场景,且事务失败可能导致数据不一致)。
Elasticsearch(搜索引擎):基于倒排索引,快速全文检索,不存储原始数据(或存储压缩数据),核心是索引和查询,适合海量文本搜索(如题目内容搜索、知识点检索),但更新延迟较高(通常1-2秒),需通过批量更新、异步索引优化。
3) 【对比与适用场景】:
| 技术名称 | 定义 | 核心特性 | 适用场景 | 注意点 |
|---|---|---|---|---|
| MySQL | 关系型数据库 | 结构化表、ACID事务、事务隔离、索引优化、分库分表/读写分离 | 题目元数据(结构化)、用户权限(结构化)、需要事务的写操作(如权限修改) | 需复杂查询时性能可能下降,需分库分表应对高并发 |
| MongoDB | 文档型NoSQL | 文档存储、灵活字段、水平扩展、最终一致性 | 题目解析、用户行为日志(非结构化)、动态字段(如用户学习进度) | 事务支持弱(多文档事务),不适合强一致性场景(如用户权限修改) |
| Elasticsearch | 搜索引擎 | 倒排索引、全文检索、分布式索引 | 题目内容搜索、知识点检索、实时搜索(如按标签、难度搜索题目) | 更新延迟(秒级),不存储原始数据(仅索引),适合搜索,不适合事务 |
| 对象存储(如阿里云OSS) | 分布式存储服务 | 存储非结构化数据(图片、视频等),通过URL引用 | 题目图片、用户上传文件 | 需要单独存储,数据库存储引用,适合大文件 |
4) 【示例】:
CREATE TABLE questions (
id INT PRIMARY KEY AUTO_INCREMENT,
content TEXT NOT NULL,
tags JSON NOT NULL, -- 存储知识点标签数组(如["算法","排序"])
difficulty INT NOT NULL, -- 难度等级(1-5)
image_url VARCHAR(255) NULL, -- 存储图片在OSS的URL
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
);
CREATE DATABASE db_algorithm;
USE db_algorithm;
CREATE TABLE questions (
id INT PRIMARY KEY AUTO_INCREMENT,
content TEXT,
tags JSON,
difficulty INT,
image_url VARCHAR(255),
created_at TIMESTAMP
);
https://oss-cn-beijing.aliyuncs.com/quiz/images/1.png,MySQL中image_url字段存储该路径。{
"_id": "user_001",
"user_id": "user_001",
"question_id": 1,
"action": "attempt",
"timestamp": ISODate("2024-01-15T10:30:00Z"),
"duration": 120 // 解题时长(秒)
}
PUT /questions/_mapping
{
"properties": {
"content": { "type": "text", "analyzer": "ik_max_word" },
"tags": { "type": "keyword" },
"difficulty": { "type": "integer" }
}
}
POST /questions/_doc/1
{
"content": "给定一个数组,找出其中最大的三个数",
"tags": ["算法", "排序"],
"difficulty": 3,
"image_url": "https://oss-cn-beijing.aliyuncs.com/quiz/images/1.png"
}
5) 【面试口播版答案】:
“面试官您好,针对竞赛题库的题目元数据(如内容、标签、难度)和用户权限数据,我建议以MySQL作为主要存储方案,结合对象存储(如阿里云OSS)和非结构化数据库(如MongoDB),以及搜索引擎(如Elasticsearch)来满足不同场景需求。
首先,MySQL作为关系型数据库,支持结构化数据存储和ACID事务,能保证题目元数据(如标签、难度)和用户权限(如角色、权限)的一致性,比如修改教师权限时,事务能保证数据完整。同时,通过分库分表(按知识点分库,如算法库、数据结构库)和读写分离(主库写,从库读),应对高并发读写,提升系统扩展性。
对于题目中的图片等非结构化数据,存储在对象存储(如阿里云OSS),数据库仅存储图片的URL,这样既能处理大文件,又不会增加数据库压力。
用户行为日志(如解题记录)用MongoDB存储,因为文档模型灵活,能动态添加字段(如解题时长),适合非结构化数据。
全文检索用Elasticsearch,比如按知识点或难度搜索题目,通过倒排索引实现快速搜索,虽然更新延迟约1-2秒,但通过批量更新、异步索引优化,对搜索体验影响较小。
核心原因是MySQL满足数据结构化、事务需求及扩展性设计,是题库系统的核心存储,而其他技术补充不同场景,形成技术栈的合理组合。”
6) 【追问清单】:
https://oss-cn-beijing.aliyuncs.com/quiz/images/1.png),结合MySQL表中的image_url字段,实现大文件存储与数据库的解耦。7) 【常见坑/雷区】: