ARTICLE DETAIL

建站实战干货

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

基于SpringBoot的音乐舞台剧分类赏析系统:从数据库到部署的毕设全解析

2026/9/9 19:07:27 拓冰建站 浏览量
基于SpringBoot的音乐舞台剧分类赏析系统:从数据库到部署的毕设全解析 每年毕业季我都会收到不少学弟学妹的私信内容基本都是同一个SpringBoot的毕设项目到底该选什么题、怎么搭框架、如何避开那些让人崩溃的坑。作为一个用SpringBoot做过好几个完整项目的老开发我太理解这种状态了。框架本身不复杂真正折磨人的是选错题、表结构设计不合理、代码写到一半发现要推倒重来。“基于SpringBoot的音乐舞台剧分类赏析系统”是我个人很推荐的一个毕业设计题目冷门但又能把SpringBoot的核心知识点全部覆盖而且业务场景好讲答辩时容易出彩。这篇文章我会从头到尾把这个项目的完整思路、数据库设计、核心模块实现、部署上线流程以及答辩准备都讲透如果你正在为毕设发愁照着这篇去复现基本不会跑偏。无论你是计算机专业应届生还是想通过实战项目熟悉SpringBoot开发的初学者这篇内容都值得你花十分钟认真读一遍。1. 项目定位与核心功能拆解1.1 为什么选音乐舞台剧分类赏析这个课题很多人选毕设题目的时候有个误区就是专挑那种烂大街的题目图书管理系统、仓库管理系统、学生信息管理系统这类题目确实稳妥但也意味着没有任何记忆点。答辩的时候老师一天要听几十个类似的项目到你的时候很难留下深刻印象。音乐舞台剧这个地方性的选题有三个好处。第一是业务差异化明显。音乐舞台剧本身涵盖面广从古典歌剧到现代音乐剧再到话剧、舞剧、儿童剧都能作为分类维度这让系统的分类设计天然有层次感而不是简单的单层列表。第二是内容展示形式丰富舞台上涉及剧目简介、角色介绍、经典唱段、幕后花絮、剧照展示、演出资讯等这些不同形态的数据对应到系统里就能演化出多种功能模块用来支撑SpringBoot的知识点完全足够。第三是用户画像清晰系统的目标用户就是文化艺术爱好者、剧场观众和高校艺术专业学生这类用户对视觉和内容质量有要求所以前端展示和后端功能都有可以发挥的空间。还有一个很实际的原因是这类带有文化属性的题目在查重和评审时有天然的叙事优势你可以说系统旨在解决音乐舞台剧信息分散、分类混乱、赏析内容缺失等问题这个角度在开题报告和论文摘要里都非常好写。1.2 系统功能模块的完整规划我在设计这个系统时把用户角色分成两类普通用户和管理员。两类角色的功能是完全分层的这是几乎所有合格毕设项目的基本要求也方便后期论文中画功能结构图。用户端的功能设计围绕“找剧目—看信息—做互动”这条主线来展开注册登录用户通过邮箱或用户名注册登录后才有权限进行收藏和评论操作游客只能浏览。分类浏览按歌剧、音乐剧、话剧、舞剧、儿童剧等一级分类展示剧目每个一级分类下还可以再按年代、题材、地区拆分出二级分类。搜索功能支持按剧目标题和关键词模糊搜索搜索结果分页展示。剧目详情与赏析展示剧目海报、基本资料导演、编剧、主演、时长、首演时间、剧情简介、艺术特色赏析、经典片段图文介绍。收藏与评论登录用户可以收藏感兴趣的音乐舞台剧也可以在详情页下方发表观后感或评论。个人中心查看自己的收藏列表、发表过的评论、修改个人资料和密码。管理端的核心职责是维护整个系统的数据剧目管理后台管理员可以新增、编辑、上下架剧目内容上传封面图。分类管理维护一级分类和二级分类调整分类排序。评论管理对用户评论进行审核删除不良内容。用户管理查看注册用户列表可以禁用异常账号。数据统计首页展示剧目总数、用户总数、评论总数等基础统计信息。这套功能规划既不臃肿又能覆盖SpringBoot开发中最常见的增删改查、分页搜索、登录鉴权、文件上传、关联查询这些知识点是一个性价比非常高的功能组合。2. 技术选型与开发环境准备2.1 SpringBoot版本与JDK搭配方案技术选型是很多同学一开始就会卡住的地方尤其是SpringBoot版本和JDK版本怎么搭配。我个人的建议是直接选择SpringBoot 2.7.x版本搭配JDK 1.8这是一个非常成熟的组合。为什么不做最新版SpringBoot 3.x已经发布不短时间了但它强制要求JDK 17以上很多学校的毕业设计运行环境还停留在JDK 8的时代而且网上能找到的大多数教程、开源代码、博客案例都基于SpringBoot 2.x真出了问题检索解决方案会方便很多。用JDK 1.8搭配SpringBoot 2.7还有一个好处是后期部署到云服务器时比较省心很多轻量应用服务器的默认Java环境就是1.8你不需要额外去折腾环境变量配置。数据库我选择的是MySQL 5.7当然你用MySQL 8.0也没问题只要注意JDBC驱动版本和连接参数略有不同就行。ORM层推荐使用MyBatis-Plus。这几乎是当前国内中小型项目和毕业设计中使用频率最高的ORM框架了因为它把单表操作的CRUD都封装好了你不需要像使用原生MyBatis那样为每个简单的操作都写XML映射文件省下的时间可以用来做更有价值的事情。前端方面我建议用Thymeleaf模板引擎加Bootstrap或者Layui这类轻量UI框架来搭建页面开发效率极高。如果学校硬性要求前后端分离那就改成SpringBoot写RESTful API前端用Vue 3加ElementPlus这个架构同样成熟只是工作量会大一些。2.2 数据库表结构设计数据库设计是毕设项目中决定成败的关键环节表设计得合理后面写代码会非常顺畅。这个系统的核心表我一一拆开讲。用户表user字段包含主键id、用户名username、加密后的密码password、昵称nickname、头像地址avatar、角色role用0表示普通用户1表示管理员、注册时间create_time。分类表category字段包含主键id、分类名称name、父分类id parent_id、排序号sort。parent_id为0时表示一级分类否则属于对应一级分类下的二级分类。这样设计的好处是支持无限级扩展虽然目前只需要两级。剧目表play字段包含主键id、剧目标题title、所属一级分类category_id、所属二级分类sub_category_id、海报封面cover、导演director、编剧writer、主演actors、剧情简介synopsis、详情内容detail这个字段存富文本内容包含完整的赏析文字和图集、演出时长duration、首演时间premiere_time、状态status0表示下架1表示上架、浏览量view_count、创建时间create_time。评论表comment字段包含主键id、用户id user_id、剧目id play_id、评论内容content、评论时间create_time、审核状态status。收藏表favorite字段包含主键id、用户id user_id、剧目id play_id、收藏时间create_time。这个表结构可以满足文章前面提到的所有功能需求。关键之处在于play表和category表的关联字段、comment表和user表以及play表的关联字段这些是后期做多表联查的基础。建议使用逻辑外键也就是不建物理外键约束只保留关联字段这样数据操作灵活度更高也避免了外键约束带来的性能问题和删除时的连锁限制。建表SQL大致如下实际项目中我习惯把字符集统一设置为utf8mb4排序规则设置为utf8mb4_general_ci这样中文存储完全没问题。CREATE TABLE category ( id int(11) NOT NULL AUTO_INCREMENT, name varchar(50) NOT NULL COMMENT 分类名称, parent_id int(11) NOT NULL DEFAULT 0 COMMENT 父分类ID0为顶级分类, sort int(11) NOT NULL DEFAULT 0 COMMENT 排序号, PRIMARY KEY (id) ) ENGINEInnoDB DEFAULT CHARSETutf8mb4 COMMENT剧目分类表; CREATE TABLE play ( id int(11) NOT NULL AUTO_INCREMENT, title varchar(100) NOT NULL COMMENT 剧目标题, category_id int(11) NOT NULL COMMENT 一级分类ID, sub_category_id int(11) DEFAULT NULL COMMENT 二级分类ID, cover varchar(255) DEFAULT NULL COMMENT 海报封面地址, director varchar(50) DEFAULT NULL COMMENT 导演, writer varchar(50) DEFAULT NULL COMMENT 编剧, actors varchar(255) DEFAULT NULL COMMENT 主演, synopsis text COMMENT 剧情简介, detail longtext COMMENT 剧目详情赏析内容, duration varchar(20) DEFAULT NULL COMMENT 演出时长, premiere_time varchar(20) DEFAULT NULL COMMENT 首演时间, view_count int(11) NOT NULL DEFAULT 0 COMMENT 浏览量, status tinyint(1) NOT NULL DEFAULT 1 COMMENT 状态0下架 1上架, create_time datetime NOT NULL DEFAULT CURRENT_TIMESTAMP, PRIMARY KEY (id) ) ENGINEInnoDB DEFAULT CHARSETutf8mb4 COMMENT剧目信息表;这里有一个容易被忽视的细节我没有给comments和favorite表建物理外键但会在评论表和收藏表中为user_id和play_id建立普通索引。这样做的目的是保留外键约束的语义同时避免外键对插入和删除性能的负面影响。在论文里你还可以把这个设计决策写进“数据库设计说明”章节解释索引代替外键的好处这是一个很加分的细节。2.3 前后端渲染方案的选择这个项目的页面渲染方式我强烈推荐Thymeleaf加服务端渲染的方式。原因很简单对于毕设项目来说服务端渲染的代码量最少调试最直观也最好写。你在Controller中返回一个视图名称Thymeleaf在服务端把数据填充到HTML模板中渲染完成后返回给浏览器整个链路非常清晰。答辩的时候老师问起请求处理流程你可以从浏览器请求讲到Controller、Service、Mapper再到数据库再把数据如何回显到页面讲一遍整个逻辑链条是完整的。当然如果你的开题报告里已经写了“基于SpringBoot和Vue的前后端分离系统”那就按前后端分离来做。这个方案用SpringBoot写RESTful接口Vue脚手架写前端页面通过Axios发送异步请求获取JSON数据。两个方案不存在谁更好只看你更熟悉哪种模式。我给的建议是如果时间紧迫就选Thymeleaf快速出成果如果想在简历上多写一条“熟悉前后端分离开发模式”那就花时间做Vue版。3. 核心业务实现与源码关键点解读3.1 登录鉴权模块的实现方式登录鉴权是几乎所有系统都必须有的模块也是答辩时老师最喜欢问的部分。这个项目我采用经典的Spring Boot拦截器实现没有引入Spring Security这种偏重的安全框架。原因是Spring Security的配置门槛对毕设来说不太友好你花大量时间去理解过滤器链和授权配置实际的业务收益并不高。用拦截器轻量实现登录状态校验代码一目了然功能上又够用。实现思路是这样用户登录成功后将用户信息存入HttpSession同时写一个LoginInterceptor拦截器在preHandle方法里检查Session中是否存在登录用户如果不存在就重定向到登录页面。注册的时候密码用MD5加盐方式加密不推荐明文存储。这里给出核心拦截器的代码片段public class LoginInterceptor implements HandlerInterceptor { Override public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception { Object user request.getSession().getAttribute(loginUser); if (user null) { // 判断是否是AJAX请求 String xRequestedWith request.getHeader(X-Requested-With); if (XMLHttpRequest.equals(xRequestedWith)) { response.setContentType(application/json;charsetUTF-8); response.getWriter().write({\code\:401,\msg\:\未登录\}); } else { response.sendRedirect(request.getContextPath() /login); } return false; } return true; } }同时我加入了管理员权限的拦截器AdminInterceptor会在拦截器逻辑里面额外校验当前Session中的用户角色是否为管理员不是就返回403提示页。在WebConfig配置类中注册拦截器时通过addPathPatterns和excludePathPatterns指定哪些路径需要拦截、哪些路径放行。静态资源、登录接口、注册接口、首页和剧目列表这些公开页面全部放行后台管理路径、收藏、评论等需要登录的接口全部拦截。这里有一个实操细节容易被新手忽略。当页面使用AJAX异步请求后端接口时如果登录态失效服务端返回的是重定向指令而不是JSON数据前端拿到302响应后会莫名其妙地跳转到一个未知页面。所以拦截器里必须判断请求是否为AJAX用X-Requested-With请求头去识别识别出来就返回JSON状态码前端再根据状态码做统一跳转处理。这个细节很多教程不会讲但在实际开发中几乎一定会遇到。3.2 分类管理模块的层级设计分类模块是整个系统看起来简单但实际设计起来有讲究的地方。我采用的是父子分类结构也就是数据库表里通过parent_id字段关联。一级分类相当于大类比如歌剧、音乐剧、话剧、舞剧、儿童剧。二级分类用来细化比如音乐剧下面可以分成百老汇经典、法语音乐剧、中文原创音乐剧。用户在首页顶部看到一级分类的导航栏鼠标悬停或点击后展示该分类下的二级分类列表。在代码实现层面因为是两级的固定结构我直接用两次查询配上VO对象来实现层级展示。先查出所有一级分类再根据每个一级分类的id查出对应二级分类列表在Service层组装成带子节点列表的对象返回给Controller。如果未来需要扩展到更多层级就可以改成递归查询的方式但毕设的体量真的不需要过度设计。public ListCategoryVO getCategoryTree() { ListCategory parentList categoryMapper.selectList( new LambdaQueryWrapperCategory().eq(Category::getParentId, 0).orderByAsc(Category::getSort)); ListCategoryVO voList new ArrayList(); for (Category parent : parentList) { CategoryVO vo new CategoryVO(); BeanUtils.copyProperties(parent, vo); ListCategory children categoryMapper.selectList( new LambdaQueryWrapperCategory().eq(Category::getParentId, parent.getId())); vo.setChildren(children); voList.add(vo); } return voList; }这段代码看起来简单但里面包含了MyBatis-Plus的LambdaQueryWrapper条件构造器的典型用法也是整个项目中使用频率最高的写法读者只要掌握了这一个写法就能轻松扩展到剧目列表、评论列表、用户列表等所有查询场景。3.3 剧目赏析内容与分页搜索剧目详情页是这个系统的内容核心我在设计详情数据的时候没有用简单的文本字段了事而是把detail字段设计为富文本HTML格式管理员在后台编辑剧目的时可以用富文本编辑器把赏析内容写成带格式的图文内容包括经典唱段的介绍、舞台美术风格的点评、代表性版本的对比分析等。数据存入数据库时是HTML字符串前端页面直接用th:utext指令输出就能完整渲染出排版效果。这里用th:utext而不是th:text就是因为th:text会转义HTML标签富文本会以纯文本形式显示一堆尖括号。这是个非常典型的踩坑点如果是自己一边摸索一边做估计要折腾半天才能找到原因。剧目列表页实现搜索加分页。搜索条件包括关键词title模糊查询和分类categoryId精确查询分页使用MyBatis-Plus内置的分页插件实现。分页插件的配置方法在官方文档里写得很清楚需要引入PaginationInnerInterceptor并注册到MybatisPlusInterceptor中。在实际使用时只需要调用Page对象传入当前页和每页大小再配合LambdaQueryWrapper条件构造器MyBatis-Plus就会自动生成带LIMIT的SQL语句。PagePlay pageInfo new Page(currentPage, pageSize); LambdaQueryWrapperPlay wrapper new LambdaQueryWrapper(); if (StringUtils.hasText(keyword)) { wrapper.like(Play::getTitle, keyword); } if (categoryId ! null) { wrapper.eq(Play::getCategoryId, categoryId); } wrapper.eq(Play::getStatus, 1).orderByDesc(Play::getCreateTime); PagePlay result playMapper.selectPage(pageInfo, wrapper);分页之后还要在页面上展示总页数和当前页码我用的是Bootstrap的分页组件Controller把pageInfo对象的current、pages、records等属性传到Model中模板引擎里循环生成页码链接再通过URL参数拼接searchKeyword和categoryId来保证换页时搜索条件不丢失。这是做列表页面时最容易出bug、也最容易被忽视的地方。很多同学做完分页后发现点第二页搜出来的是空数据就是因为只传了页码没有把搜索条件一起传过去。3.4 后台管理端的文件上传与权限控制后台管理端我单独设计了一套页面路径前缀是/admin所有该前缀下的请求都经过管理员拦截器校验。管理功能主要聚焦在剧目管理、分类管理、评论管理和用户管理。剧目管理页面使用表格展示所有剧目每条记录后面跟编辑和删除按钮。新增和编辑用到同一个表单页面点击保存时通过主键id是否为空判断是执行insert还是update这个逻辑在Service层通过saveOrUpdate方法统一封装。删除剧目时同时要删除该剧目关联的评论和收藏数据否则会留下脏数据。我在删除接口里写了三个逻辑删除语句这个细节在答辩时主动讲出来会让老师觉得你考虑问题非常周全。文件上传功能用来上传海报封面图。我用的方案是本地磁盘存储在配置文件中指定一个存储路径SpringBoot接收MultipartFile类型参数后将文件写入指定目录然后把文件的访问URL映射为本地路径。要注意的是一定要对上传文件类型做校验不能只检查扩展名还要检查ContentType和文件大小。我只允许jpeg、png、jpg、webp这四种图片格式单张限制在2MB以内。这些限制条件既保证了系统稳定也防止了用户上传超大文件占用磁盘空间。提示如果你把项目部署到云服务器图片上传的绝对路径不要写死放到application配置文件中用${upload.path}引用方便不同环境切换。4. 项目运行部署与常见问题排查4.1 本地启动的完整流程我在这里把项目从获取源码到本地跑起来的完整流程整理出来按这个顺序操作百分之百能启动成功。第一步准备环境安装JDK 1.8配置JAVA_HOME环境变量安装Maven 3.6或以上版本安装MySQL 5.7并创建数据库建议数据库名就叫stage_show或者theater字符集选择utf8mb4。第二步导入数据库用Navicat或命令行工具执行项目附带的sql脚本。第三步在IDEA中导入项目等待Maven下载依赖国内网络环境下建议把Maven中央仓库镜像改成阿里云镜像否则第一次加载依赖可能会非常漫长。第四步修改application.yml文件把数据库的URL、用户名、密码改成自己本地的配置。第五步运行启动类中main方法看到SpringBoot的启动日志中出现Tomcat started on port(s): 8080就表示启动成功。我在实际帮助很多学弟学妹排查启动问题时发现90%的问题出在数据库连接参数上。最典型的是时区问题控制台会报警告提示The server time zone value is unrecognized解决办法是在数据库连接URL中加上serverTimezoneAsia/Shanghai。另一个是SSL连接警告如果不需要SSL可以在URL后追加useSSLfalse。spring: datasource: url: jdbc:mysql://localhost:3306/stage_show?useUnicodetruecharacterEncodingutf8serverTimezoneAsia/ShanghaiuseSSLfalse username: root password: 123456 driver-class-name: com.mysql.cj.jdbc.Driver4.2 服务器部署的两种方式本地跑通之后多数学校还要求演示线上部署版本或者说你想把项目链接放进简历里那就需要部署到云服务器。最直接的方式是Maven把项目打成jar包然后上传到服务器运行。在IDEA的Maven面板中执行clean和package指令target目录下会生成一个jar文件通过SCP或其他工具上传到服务器任意目录后使用nohup命令在后台启动nohup java -jar stage-show-0.0.1-SNAPSHOT.jar --server.port8080 app.log 21 日志会输出到app.log文件中想要实时查看运行日志就用tail -f app.log。这种部署方式也叫“手动部署”优点是快速直接适合毕设演示。如果你想展示Docker容器化部署的能力也可以写一个Dockerfile把项目打包成镜像运行这个操作在简历上是一个实打实的加分项。Docker部署的核心是把运行环境和应用本身打包到一起我给的Dockerfile大致是这样FROM openjdk:8-jdk-alpine WORKDIR /app COPY target/stage-show-0.0.1-SNAPSHOT.jar app.jar EXPOSE 8080 ENTRYPOINT [java, -jar, app.jar]然后用docker build构建镜像docker run启动容器再配合端口映射就可以用服务器IP加端口访问系统了。服务器上如果还有Nginx可以把Nginx配置为反向代理将域名指向SpringBoot服务端口顺便把图片上传目录通过location映射成静态资源访问路径。4.3 常见问题速查表我整理了这份项目从开发到部署过程中最高频的几类问题每一个都是我亲测遇到过的按图索骥能省下大把排错时间。问题现象根本原因解决办法启动时报数据库时区错误MySQL连接URL没加serverTimezone在URL末尾添加serverTimezoneAsia/Shanghai启动报端口被占用本机8080端口已被其他程序占用修改yml中server.port或关闭占用进程报Invalid bound statement异常Mapper接口和XML文件映射不上检查XML文件所在路径是否和Mapper接口包路径一致检查namespace是否写对页面中文乱码请求或响应编码格式不一致在配置中统一characterEncodingutf8确保页面模板也设置UTF-8静态资源404自定义拦截器拦截了静态资源路径在拦截器排除路径中加入/static/、/uploads/等资源前缀上传图片后无法访问SpringBoot未映射本地文件目录配置资源映射将本地磁盘目录映射为URL访问路径部署到服务器后前端样式丢失使用了相对路径但页面URL层级不对模板中统一使用th:href{/css/...}方式引用资源数据库连接断开报错MySQL默认空闲超时时间过短在连接URL中设置autoReconnecttrue或配置连接池的keepAlive这些问题的排查思路其实有一个共性优先检查配置文件再检查注解和依赖最后考虑环境差异。按这个顺序排查通常都能很快定位。5. 毕业设计加分项与答辩准备5.1 从开发视角挖掘项目亮点很多同学答辩时只会在PPT上展示页面截图然后说“我用了SpringBoot和MyBatis-Plus开发了这个系统”这太可惜了。同样一个系统换个表述方式就能让老师觉得你做的工作量和技术含量完全不同。列举几个可以包装的亮点方向。第一是全局异常处理我在所有Controller层中没有用一堆try-catch而是通过RestControllerAdvice配合ExceptionHandler统一处理业务异常给用户返回友好的错误提示同时记录异常日志。这在项目里虽然只有几十行代码但体现的是规范化开发的意识。第二是参数校验我在接收前端参数的实体类上用NotBlank、Size等注解做基础校验避免了写一堆if判断。第三是统一返回对象Result封装后端接口全部用code、msg、data三个字段的JSON结构返回代码风格统一前端处理逻辑也简洁。第四是数据统计模块配合Echarts做了简单的可视化图表展示虽然图表不复杂但在视觉效果上立刻提升一个档次。这些点不需要每一项都是高深技术关键是让老师看到你写代码有工程化思维而不只是把CRUD拼凑起来能跑。5.2 答辩高频问题与回答思路根据我带过的学生答辩经验老师对这个题目的提问方向往往集中在下面几个问题上。第一个问题为什么选择这个课题回答思路从两个层面展开。业务层面上讲音乐舞台剧作为文化艺术的重要组成部分目前缺少一个系统性的分类和信息整合平台本项目希望通过技术手段帮助用户更便捷地了解和赏析优秀剧目。技术层面上讲SpringBoot框架成熟、开发效率高适合作为毕业设计的技术载体通过这个项目可以系统性地锻炼Web全栈开发能力。第二个问题数据表之间是什么关系回答时要描述清楚分类表和剧目表是一对多关系剧目表和评论表是一对多关系用户表和评论表是一对多关系用户表和收藏表是多对多关系通过favorite表消除冗余关联。能画ER图就现场画画不了就口头描述清楚。第三个问题权限控制是怎么实现的回答重点说明拦截器的使用和Session机制。可以主动提到自己如何区分普通用户接口和管理员接口如何通过拦截器统一校验登录状态和管理员角色。如果再往深了说可以提一句“项目当前使用的是基于Session的会话管理如果要扩展成分布式系统可以考虑改为JWT令牌机制”这句话说明你了解会话管理的演进方向是很好的加分表述。第四个问题系统还能怎么扩展这个问题考验的是对当前系统局限性的认知。可以从三个方向回答增加推荐算法根据用户收藏和浏览历史推荐相似剧目引入OSS对象存储解决本地存储扩展性差的问题对接真实的演出票务平台实现在线选座购票功能。回答时不要空谈要结合当前表结构和已有功能来谈改造点。注意答辩时遇到不会的问题不要硬编坦诚地说“这个思路我之前没有深入考虑过但根据我的理解可以如何如何”反而能获得老师的认可。所有答辩准备的根本前提是你真的亲自动手把代码写了一遍。写在最后的一些个人体会这套项目从我最初搭骨架到整个功能跑通大概用了一周左右的业余时间。我的体会是永远不要等所有功能想清楚了再开始写代码。先把SpringBoot项目跑起来数据库建好登录注册做通后面每个功能就是往这个骨架里不断地填内容越做越有感觉焦虑感也会小很多。而且这个项目的代码结构留了很充裕的扩展空间后续想要加音乐在线试听、演出票务信息聚合、用户评分排行等功能都能在现有表结构基础上平滑扩展。我也建议拿到源码后不要直接交作业亲手把每个核心模块的代码逻辑走一遍把Controller、Service、Mapper这层调用关系看清楚。只有自己动手改过几个功能、修过几个Bug答辩的时候才有底气工作中面试官问你项目经验时也才讲得出真实的细节。