【JAVA程序设计】基于SpringBoot+vue的在线考试系统-以计算机网络为例,可自行录入题库-附下载地址

news2024/12/25 1:32:11

基于SpringBoot+vue的在线考试系统-以计算机网络为例,可自行录入题库

    • 一、项目简介
    • 二、开发环境
    • 三、项目技术
    • 四、功能结构
    • 五、运行截图
    • 六、功能实现
    • 七、数据库设计
    • 八、源码下载地址

一、项目简介

随着信息技术的迅猛发展,教育行业正面临着巨大的变革和挑战。为了适应当下时代的需求,我们开发了一款现代化的在线考试系统,旨在提供高效、便捷、安全的考试环境,为学生和教师带来更好的考试体验和教学管理。

我们的在线考试系统采用了先进的技术架构,其中后端采用了Spring Boot,前端则采用Vue2和ElementUI。同时,作为数据库,我们选择了MySQL,以保障数据的可靠性和稳定性。

该系统提供了全面的功能模块,涵盖学生管理、教师管理、题库管理、考试管理、留言、在线考试和成绩统计等方面。学生管理模块包含学生信息的录入、查询和修改功能,教师管理模块提供了教师信息信息添加、删除功能,题库管理模块允许教师对题目进行增加于查看,考试管理模块支持考试计划创建、考试计划修改以及删除等操作,留言功能方便学生和教师之间的交流,而在线考试模块则为学生提供了在线答题和交卷的便捷方式并且提供自动判分。成绩统计模块则帮助教师对学生的考试成绩进行全面统计和分析,为教学提供有效参考。

二、开发环境

开发环境版本/工具
基础环境Jdk1.8、node.js14
开发工具IntelliJ IDEA、WebStorm
操作系统Windows 10
内存要求8GB 以上
浏览器Firefox (推荐)、Google Chrome (推荐)、Edge
数据库MySQL 8.0 (推荐)
数据库工具Navicat Premium 15 (推荐)
项目框架后端SpringBoot、前端ElementUi

三、项目技术

后端:SpringBoot、MybatisPlus、MySQL

前端:Vue2、ElementUi、vue-router、vuex、JavaScript

四、功能结构

学生管理功能 : 学生管理模块允许学生进行个人信息的修改和添加,保证学生信息的及时更新。学生登录功能为学生提供了便捷的访问入口,让他们可以方便地查看考试计划、参加在线考试,并随时查询个人的考试成绩。

教师管理功能 : 教师管理模块为教师提供了个人信息的管理功能,教师可以随时修改和添加自己的信息。通过教师登录功能,教师可以查看自己负责的考试和班级,进行考试的修改和删除等操作,实现对教学事务的全面管理。

题库管理功能 : 题库管理模块为教师提供了方便快捷的试卷题库添加功能,支持多种题型的题目录入。教师可以查看已有的题库,便于组卷时参考。同时,试卷在线组卷功能可以根据需要自动生成试卷,减轻了教师的工作负担。

考试管理功能 : 考试管理模块支持考试计划的添加、修改和删除,教师可以根据学习进度和课程需要进行灵活安排。考试的修改功能也让教师在出现变动时能够及时调整考试安排,保证教学进度的顺利进行。

成绩查询功能 : 成绩查询功能允许学生方便地查询自己的考试成绩,而且考试分段成绩统计功能可以为教师提供更全面的学生成绩分析,辅助教学改进和个性化辅导。

在线考试客户端 : 在线考试客户端为学生提供了便捷的在线考试体验。学生可以在客户端查看考试计划,准时参加在线答题考试,并通过自动判分功能快速获取考试成 绩。客户端还支持留言功能,学生可以向教师提问或反馈问题,促进师生间的有效沟通。
在这里插入图片描述

五、运行截图

考试计划查看:
在这里插入图片描述
在线考试:
在这里插入图片描述

提交考试:
在这里插入图片描述

考试成绩查看:
在这里插入图片描述
留言板:
在这里插入图片描述

登录页面:
在这里插入图片描述

考试管理:
在这里插入图片描述
在这里插入图片描述

题库管理:
在这里插入图片描述在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

教师管理:
在这里插入图片描述
在这里插入图片描述

学生管理:
在这里插入图片描述
在这里插入图片描述

留言:
在这里插入图片描述

考试成绩统计:
在这里插入图片描述
在这里插入图片描述

六、功能实现

前端获取当前考试信息

    getExamData() { //获取当前试卷所有信息
      let date = new Date()
      this.startTime = this.getTime(date)
      let examCode = this.$route.query.examCode //获取路由传递过来的试卷编号
      this.$axios(`/api/exam/${examCode}`).then(res => {  //通过examCode请求试卷详细信息
        this.examData = { ...res.data.data} //获取考试详情
        this.index = 0
        this.time = this.examData.totalScore //获取分钟数
        let paperId = this.examData.paperId
        this.$axios(`/api/paper/${paperId}`).then(res => {  //通过paperId获取试题题目信息
          this.topic = {...res.data}
          let reduceAnswer = this.topic[1][this.index]
          this.reduceAnswer = reduceAnswer
          let keys = Object.keys(this.topic) //对象转数组
          keys.forEach(e => {
            let data = this.topic[e]
            this.topicCount.push(data.length)
            let currentScore = 0
            for(let i = 0; i< data.length; i++) { //循环每种题型,计算出总分
              currentScore += data[i].score
            }
            this.score.push(currentScore) //把每种题型总分存入score
          })
          let len = this.topicCount[1]
          let father = []
          for(let i = 0; i < len; i++) { //根据填空题数量创建二维空数组存放每道题答案
            let children = [null,null,null,null]
            father.push(children)
          }
          this.fillAnswer = father
          let dataInit = this.topic[1]
          this.number = 1
          this.showQuestion = dataInit[0].question
          this.showAnswer = dataInit[0]
        })
      })
    }

自动判分方法核心代码

   commit() { //答案提交计算分数
      /* 计算选择题总分 */
      let topic1Answer = this.topic1Answer
      let finalScore = 0
      topic1Answer.forEach((element,index) => { //循环每道选择题根据选项计算分数
        let right = null
        if(element != null) {
          switch(element) { //选项1,2,3,4 转换为 "A","B","C","D"
            case 1:
              right = "A"
              break
            case 2:
              right = "B"
              break
            case 3:
              right = "C"
              break
            case 4:
              right = "D"
          }
          if(right == this.topic[1][index].rightAnswer) { // 当前选项与正确答案对比
            finalScore += this.topic[1][index].score // 计算总分数
          }
          console.log(right,this.topic[1][index].rightAnswer)
        }
        // console.log(topic1Answer)
      })
      /**计算判断题总分 */
      // console.log(`this.fillAnswer${this.fillAnswer}`)
      // console.log(this.topic[2][this.index])
      let fillAnswer = this.fillAnswer
      fillAnswer.forEach((element,index) => { //此处index和 this.index数据不一致,注意
        element.forEach((inner) => {
          if(this.topic[2][index].answer.includes(inner)) { //判断填空答案是否与数据库一致
            console.log("正确")
            finalScore += this.topic[2][this.index].score
          }
        })
      });
      /** 计算判断题总分 */
      let topic3Answer = this.judgeAnswer
      topic3Answer.forEach((element,index) => {
        let right = null
        switch(element) {
          case 1:
            right = "T"
            break
          case 2:
            right = "F"
        }
        if(right == this.topic[3][index].answer) { // 当前选项与正确答案对比
            finalScore += this.topic[3][index].score // 计算总分数
          }
      })
      if(this.time != 0) {
        this.$confirm("考试结束时间未到,是否提前交卷","友情提示",{
          confirmButtonText: '立即交卷',
          cancelButtonText: '再检查一下',
          type: 'warning'
        }).then(() => {
          console.log("交卷")
          let date = new Date()
          this.endTime = this.getTime(date)
          let answerDate = this.endTime.substr(0,10)
          //提交成绩信息
          this.$axios({
            url: '/api/score',
            method: 'post',
            data: {
              examCode: this.examData.examCode, //考试编号
              studentId: this.userInfo.id, //学号
              subject: this.examData.source, //课程名称
              etScore: finalScore, //答题成绩
              answerDate: answerDate, //答题日期
            }
          }).then(res => {
            if(res.data.code == 200) {
              this.$router.push({path:'/studentScore',query: {
                score: finalScore,
                startTime: this.startTime,
                endTime: this.endTime
              }})
            }
          })
        }).catch(() => {
          console.log("继续答题")
        })
      }
    },

后端获取考试信息接口

    @GetMapping("/exam/{examCode}")
    public ApiResult findById(@PathVariable("examCode") Integer examCode){
        System.out.println("根据ID查找");
        ExamManage res = examManageService.findById(examCode);
        if(res == null) {
            return ApiResultHandler.buildApiResult(10000,"考试编号不存在",null);
        }
        return ApiResultHandler.buildApiResult(200,"请求成功!",res);
    }

后端获取试题接口

    @GetMapping("/paper/{paperId}")
    public Map<Integer, List<?>> findById(@PathVariable("paperId") Integer paperId) {
        List<MultiQuestion> multiQuestionRes = multiQuestionService.findByIdAndType(paperId);   //选择题题库 1
        List<FillQuestion> fillQuestionsRes = fillQuestionService.findByIdAndType(paperId);     //填空题题库 2
        List<JudgeQuestion> judgeQuestionRes = judgeQuestionService.findByIdAndType(paperId);   //判断题题库 3
        Map<Integer, List<?>> map = new HashMap<>();
        map.put(1,multiQuestionRes);
        map.put(2,fillQuestionsRes);
        map.put(3,judgeQuestionRes);
        return  map;
    }

七、数据库设计

表名:admin

字段名称数据类型是否必填注释
adminIdint(11)ID号
adminNamevarchar(20)姓名
sexvarchar(2)性别
telvarchar(11)电话号码
emailvarchar(20)电子邮箱
pwdvarchar(16)密码
cardIdvarchar(18)身份证号
rolevarchar(1)角色(0管理员,1教师,2学生)

表名:exam_manage

字段名称数据类型是否必填注释
examCodeint(11)考试编号
descriptionvarchar(50)该次考试介绍
sourcevarchar(20)课程名称
paperIdint(11)试卷编号
examDatevarchar(10)考试日期
totalTimeint(11)持续时长
gradevarchar(10)年级
termvarchar(10)学期
majorvarchar(20)专业
institutevarchar(20)学院
totalScoreint(11)总分
typevarchar(255)考试类型
tipsvarchar(255)考生须知

表名:fill_question

字段名称数据类型是否必填注释
questionIdint(11)试题编号
subjectvarchar(20)考试科目
questionvarchar(255)试题内容
answervarchar(255)正确答案
analysisvarchar(255)题目解析
scoreint(11)分数
levelvarchar(5)难度等级
sectionvarchar(20)所属章节

表名:judge_question

字段名称数据类型是否必填注释
questionIdint(11)试题编号
subjectvarchar(20)考试科目
questionvarchar(255)试题内容
answervarchar(255)正确答案
analysisvarchar(255)题目解析
scoreint(11)分数
levelvarchar(1)难度等级
sectionvarchar(20)所属章节

表名:message

字段名称数据类型是否必填注释
idint(11)留言编号
titlevarchar(20)标题
contentvarchar(255)留言内容
timedate留言时间

八、源码下载地址

原创项目,开发不易,保证项目经过多人调试与测试,可以准确无误运行(经过最新调试,系统依旧可以持续运行

项目获取地址:

#浏览器打开一下官方网站进行项目源码下载
www.shiyuncode.com/productlist/2?search=%E8%80%83%E8%AF%95

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/891447.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

Docker容器安装mysql 8 教程

一、 安装Docker&#xff0c;Docker安装过程如下&#xff1a; 1、卸载系统之前的 docker sudo yum remove docker \docker-client \docker-client-latest \docker-common \docker-latest \docker-latest-logrotate \docker-logrotate \docker-engine 2、安装 Docker-CE 安装…

vue利用 sortable 完成表格拖拽

先讲一下vue2&#xff0c;使用sortable完成表格拖拽【不只是表格&#xff0c;div也可以实现&#xff0c;但我项目中是表格拖拽】 github地址 安装 npm install sortablejs --save使用 &#xff08;我的项目中是拖拽一个小按钮移动&#xff0c;而不是整行&#xff09; <te…

字符设备分布注册实现LED灯

目标&#xff1a;通过字符设备的分布注册实现LED灯的控制 字符分布注册&#xff1a; test.c文件 #include <stdio.h> #include <unistd.h> #include <sys/types.h> #include <sys/stat.h> #include <fcntl.h> #include <stdlib.h> #incl…

212、仿真-基于51单片机体温脉搏心率血氧报警Proteus仿真设计(程序+Proteus仿真+配套资料等)

毕设帮助、开题指导、技术解答(有偿)见文未 目录 一、硬件设计 二、设计功能 三、Proteus仿真图 四、程序源码 资料包括&#xff1a; 需要完整的资料可以点击下面的名片加下我&#xff0c;找我要资源压缩包的百度网盘下载地址及提取码。 方案选择 单片机的选择 方案一&a…

快速解决Ubuntu 中 wine 程序 中文显示为方块/显示错误/无法显示中文(2023)

解决办法就是在创建prefix的命令行里加上LANG“zh_CN.UTF8” LC_ALL“zh_CN.UTF8”&#xff0c;并安装cjkfonts&#xff0c;即可。 1、生成prefix、安装cjk字体 以下是基本流程&#xff1a; 现在假定wine和winetricks已经装好&#xff0c; // 先创建一个prefix&#xff0c;按…

切面的魔力:解密Spring AOP 面向切面编程

目录 一、AOP简介 1.1 什么是AOP &#xff1f; 1.2 什么是面向切面编程 &#xff1f; 1.3 AOP 的特点 二、 AOP的基本概念解读 2.1 AOP的基本概念 2.2 AOP 概念趣事解读 三、代码情景演示 3.1 编写目标对象&#xff08;超级英雄们正常的行动&#xff09; 3.2 编写通知…

史上最全HBase面试题,高薪必备,架构必备

说在前面 本文《尼恩 大数据 面试宝典》 是 《尼恩Java面试宝典》姊妹篇。 这里特别说明一下&#xff1a;《尼恩Java面试宝典》41个专题 PDF 自首次发布以来&#xff0c; 已经汇集了 好几千题&#xff0c;大量的大厂面试干货、正货 &#xff0c;足足4800多页&#xff0c;帮助…

【脚踢数据结构】常见排序算法

(꒪ꇴ꒪ )&#xff0c;Hello我是祐言QAQ我的博客主页&#xff1a;C/C语言&#xff0c;Linux基础&#xff0c;ARM开发板&#xff0c;软件配置等领域博主&#x1f30d;快上&#x1f698;&#xff0c;一起学习&#xff0c;让我们成为一个强大的攻城狮&#xff01;送给自己和读者的…

keil遇到“Error:CreateProcess failed,Command:“怎么办

解决办法&#xff1a; 第一步&#xff1a;卸载原有的compiler 5; 第二步&#xff1a;安装compiler 5到指定目录&#xff1a;这个目录地址是&#xff1a; 安装目录地址“ARM安装目录” / ARMARM_Compiler_5.06u7 例如我的安装目录是C:\Keil_v5\ARM\ARM_Compiler_5.06u7 第三…

苹果电脑清理软件——CleanMyMac快速清理电脑垃圾

大家在用苹果电脑卸载软件时是不是很苦恼&#xff1f;遇到要清理的垃圾软件太多&#xff0c;总是清理不干净。这时可以借助苹果电脑清理软件——CleanMyMac快速清理&#xff0c;接下来的文章就教教大家快速清理电脑垃圾软件&#xff0c;怎么快速清理电脑垃圾软件。 CleanMyMac …

LangChain手记 Evalutation评估

整理并翻译自DeepLearning.AILangChain的官方课程&#xff1a;Evaluation&#xff08;源代码可见&#xff09; 基于LLM的应用如何做评估是一个难点&#xff0c;本节介绍了一些思路和工具。 “从传统开发转换到基于prompt的开发&#xff0c;开发使用LLM的应用&#xff0c;整个工…

云农场种植模式:数字化农业的崭新未来

在现代科技的映衬下&#xff0c;农业正在经历着前所未有的变革。云农场种植模式作为数字化农业的一个重要组成部分&#xff0c;为农业注入了新的活力和可能性。这种创新模式不仅提升了农业效率&#xff0c;还为农民、消费者以及环境带来了许多积极影响。 云农场种植模式玩法说明…

vue实现可缩放拖拽盒子(亲测可用)

特征 没有依赖 使用可拖动&#xff0c;可调整大小或两者兼备定义用于调整大小的句柄限制大小和移动到父元素或自定义选择器将元素捕捉到自定义网格将拖动限制为垂直或水平轴保持纵横比启用触控功能使用自己的样式为句柄提供自己的样式 安装和基本用法 npm install --save vue-d…

解决“warning: #223-D: function “xPortSysTickHandler“ declared implicitly“告警提示

继上篇文章发布已有时隔两个月之久&#xff0c;今天就把这两个月遇到的一些问题解决分享一下&#xff0c;首先&#xff0c;我们来看今天分享的这个关于我在学习freertos遇到的一个告警。如图所示&#xff1a; 告警提示原句为&#xff1a; warning: #223-D: function "xP…

DNDC模型建模方法及土壤碳储量、温室气体排放、农田减排、土地变化、气候变化应用

DNDC&#xff08;Denitrification-Decomposition&#xff0c;反硝化-分解模型&#xff09;是目前国际上最为成功的模拟生物地球化学循环的模型之一&#xff0c;自开发以来&#xff0c;经过不断完善和改进&#xff0c;从模拟简单的农田生态系统发展成为可以模拟几乎所有陆地生态…

BAT测试专家对web测试和APP测试的总结

单纯从功能测试的层面上来讲的话&#xff0c;App 测试、Web 测试在流程和功能测试上是没有区别的&#xff0c;但由于系统结构方面存在差异&#xff08;web 项目&#xff0c;b/s 架构&#xff1b;app 项目&#xff0c;c/s 结构&#xff09;在测试中还是有不同的侧重点内容&#…

SOLIDWORKS 弹簧扣特征-塑料制品的福音

很多从事塑料制品产业的工程师&#xff0c;每天都在面对如何提高配合精度的问题&#xff0c;特别是扣合的精度。通常情况下扣合类结构采用分开建立扣与槽的形式&#xff0c;该方式已经无法满足当前环境下设计的需要&#xff0c;当然在SOLIDWORKS中此类问题很早之前就已经被考虑…

扁线电机定子转子工艺及自动化装备

售&#xff1a;扁线电机 电驱对标样件 需要请联&#xff1a;shbinzer &#xff08;拆车邦&#xff09; 新能源车电机路线大趋势&#xff0c;自动化装配产线需求迫切永磁同步电机是新能源车驱动电机的主要技术路线。目前新能源车上最广泛应用的类型为永磁同步电机&#xff0c…

数组的详述(2)

2、二维数组的创建和初始化 可以把二维数组理解为一维数组的数组。 行 列 //行可省略&#xff0c;列不能省。 二维数组的使用&#xff08;<而不是<&#xff0c;因为数组下标第一个是0&#xff09; 二维数组在内存中的储存​​​​&#xf…

day4 驱动开发

【ioctl函数的使用】 1.概述 linux有意将对设备的功能选择和设置以及硬件数据的读写分成不同的函数来实现。让read/write函数专注于数据的读写&#xff0c;而硬件功能的设备和选择通过ioctl函数来选择 2.ioctl函数分析 int ioctl(int fd,unsigned long request) 通过&…