Переглянути джерело

Merge branch 'dev_v2.1.0' of http://git.qmth.com.cn/wangliang/distributed-print-service into dev_v2.1.0

xiaof 4 роки тому
батько
коміт
1b5d1416a7
37 змінених файлів з 2041 додано та 367 видалено
  1. 2 0
      teachcloud-common/src/main/java/com/qmth/teachcloud/common/enums/ExceptionResultEnum.java
  2. 92 0
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/dto/AnswerDetailBean.java
  3. 83 0
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/CellResult.java
  4. 98 0
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/CollegeAndCourseResult.java
  5. 47 0
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/CollegeAndSchoolGradeDistributionResult.java
  6. 6 6
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/CourseDimensionResult.java
  7. 35 0
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/DimensionAnalyzeResult.java
  8. 89 0
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/DimensionInfoResult.java
  9. 20 6
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/ExamRecordResult.java
  10. 58 0
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/GradeDistributionResult.java
  11. 71 0
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/ModuleDimensionResult.java
  12. 47 0
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/PaperTypeResult.java
  13. 94 0
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/PiecewiseDistributionResult.java
  14. 35 0
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/QuestionInfoResult.java
  15. 35 0
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/QuestionListResult.java
  16. 59 0
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/QuestionResult.java
  17. 17 3
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/TBAnswerResult.java
  18. 35 0
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/TeacherInfoListResult.java
  19. 13 0
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/entity/TAExamCourseRecordDio.java
  20. 13 0
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/entity/TAExamCourseRecordMod.java
  21. 173 28
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/entity/TAPaperStruct.java
  22. 33 0
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/enums/GradeScopeEnum.java
  23. 38 0
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/enums/PiecewiseScopeEnum.java
  24. 11 0
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/mapper/TBAnswerMapper.java
  25. 49 20
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/service/AnalyzeForReportService.java
  26. 46 2
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/service/ReportCommonService.java
  27. 2 2
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/service/TAExamCourseService.java
  28. 11 0
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/service/TBAnswerService.java
  29. 268 145
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/service/impl/AnalyzeForReportServiceImpl.java
  30. 291 12
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/service/impl/ReportCommonServiceImpl.java
  31. 15 38
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/service/impl/TAExamCourseServiceImpl.java
  32. 7 0
      teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/service/impl/TBAnswerServiceImpl.java
  33. 1 0
      teachcloud-report-business/src/main/resources/mapper/TAExamCourseRecordMapper.xml
  34. 25 1
      teachcloud-report-business/src/main/resources/mapper/TBAnswerMapper.xml
  35. 95 91
      teachcloud-report/src/main/java/com/qmth/teachcloud/report/api/BasicDatasourceController.java
  36. 1 1
      teachcloud-report/src/main/java/com/qmth/teachcloud/report/api/CourseController.java
  37. 26 12
      teachcloud-report/src/test/java/com/qmth/teachcloud/report/AnalyzeForStudentServiceTest.java

+ 2 - 0
teachcloud-common/src/main/java/com/qmth/teachcloud/common/enums/ExceptionResultEnum.java

@@ -81,6 +81,8 @@ public enum ExceptionResultEnum {
 
     DATA_COUNT_EXCEPTION(HttpStatus.INTERNAL_SERVER_ERROR, 5000031, "得到的数据条数异常,应该有且仅有一条数据"),
 
+    DATA_ERROR(HttpStatus.INTERNAL_SERVER_ERROR, 5000032, "数据异常"),
+
     /**
      * 401
      */

+ 92 - 0
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/dto/AnswerDetailBean.java

@@ -0,0 +1,92 @@
+package com.qmth.teachcloud.report.business.bean.dto;
+
+import io.swagger.annotations.ApiModelProperty;
+
+import java.io.Serializable;
+
+/**
+ * @Description: answerDetailBean
+ * @Param:
+ * @return:
+ * @Author: wangliang
+ * @Date: 2021/1/14
+ */
+public class AnswerDetailBean implements Serializable {
+    @ApiModelProperty(value = "试卷id")
+    private Long paperId;
+
+    @ApiModelProperty(value = "试卷类型")
+    private String paperType;
+
+    @ApiModelProperty(value = "得分率")
+    private Double scoreRate;
+
+    @ApiModelProperty(value = "难度")
+    private String difficult;
+
+    @ApiModelProperty(value = "学院名称")
+    private String collegeName;
+
+    @ApiModelProperty(value = "学院id")
+    private Long collegeId;
+
+    public AnswerDetailBean(Long paperId, String paperType, Double scoreRate, String difficult, String collegeName, Long collegeId) {
+        this.paperId = paperId;
+        this.paperType = paperType;
+        this.scoreRate = scoreRate;
+        this.difficult = difficult;
+        this.collegeName = collegeName;
+        this.collegeId = collegeId;
+    }
+
+    public AnswerDetailBean() {
+    }
+
+    public Long getPaperId() {
+        return paperId;
+    }
+
+    public void setPaperId(Long paperId) {
+        this.paperId = paperId;
+    }
+
+    public String getPaperType() {
+        return paperType;
+    }
+
+    public void setPaperType(String paperType) {
+        this.paperType = paperType;
+    }
+
+    public Double getScoreRate() {
+        return scoreRate;
+    }
+
+    public void setScoreRate(Double scoreRate) {
+        this.scoreRate = scoreRate;
+    }
+
+    public String getDifficult() {
+        return difficult;
+    }
+
+    public void setDifficult(String difficult) {
+        this.difficult = difficult;
+    }
+
+    public String getCollegeName() {
+        return collegeName;
+    }
+
+    public void setCollegeName(String collegeName) {
+        this.collegeName = collegeName;
+    }
+
+    public Long getCollegeId() {
+        return collegeId;
+    }
+
+    public void setCollegeId(Long collegeId) {
+        this.collegeId = collegeId;
+    }
+}

+ 83 - 0
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/CellResult.java

@@ -0,0 +1,83 @@
+package com.qmth.teachcloud.report.business.bean.result;
+
+import io.swagger.annotations.ApiModelProperty;
+
+import java.io.Serializable;
+import java.math.BigDecimal;
+
+/**
+ * @Description: CellResult
+ * @Param:
+ * @return:
+ * @Author: wangliang
+ * @Date: 2021/6/11
+ */
+public class CellResult implements Serializable {
+
+    @ApiModelProperty(value = "简介")
+    private String interpret;
+
+    @ApiModelProperty(value = "分数")
+    private String scope;
+
+    @ApiModelProperty(value = "学院平均分得分率")
+    private Double colAvgScoreRate;
+
+    @ApiModelProperty(value = "学校平均分得分率")
+    private Double schAvgScoreRate;
+
+    @ApiModelProperty(value = "计数")
+    private Integer count;
+
+    public CellResult() {
+
+    }
+
+    public CellResult(String interpret, String scope, Double colAvgScoreRate, Double schAvgScoreRate, Integer count) {
+        this.interpret = interpret;
+        this.scope = scope;
+        this.colAvgScoreRate = colAvgScoreRate;
+        this.schAvgScoreRate = schAvgScoreRate;
+        this.count = count;
+    }
+
+    public String getInterpret() {
+        return interpret;
+    }
+
+    public void setInterpret(String interpret) {
+        this.interpret = interpret;
+    }
+
+    public String getScope() {
+        return scope;
+    }
+
+    public void setScope(String scope) {
+        this.scope = scope;
+    }
+
+    public Double getColAvgScoreRate() {
+        return colAvgScoreRate;
+    }
+
+    public void setColAvgScoreRate(Double colAvgScoreRate) {
+        this.colAvgScoreRate = colAvgScoreRate;
+    }
+
+    public Double getSchAvgScoreRate() {
+        return schAvgScoreRate;
+    }
+
+    public void setSchAvgScoreRate(Double schAvgScoreRate) {
+        this.schAvgScoreRate = schAvgScoreRate;
+    }
+
+    public Integer getCount() {
+        return count;
+    }
+
+    public void setCount(Integer count) {
+        this.count = count;
+    }
+}

+ 98 - 0
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/CollegeAndCourseResult.java

@@ -0,0 +1,98 @@
+package com.qmth.teachcloud.report.business.bean.result;
+
+import com.sun.source.doctree.SerialDataTree;
+import io.swagger.annotations.ApiModelProperty;
+
+import java.io.Serializable;
+import java.util.List;
+
+/**
+ * @Description: 学院学科result
+ * @Param:
+ * @return:
+ * @Author: wangliang
+ * @Date: 2021/6/11
+ */
+public class CollegeAndCourseResult implements Serializable {
+
+    @ApiModelProperty(value = "courseInfo")
+    private CourseInfoResult courseInfo;
+
+    @ApiModelProperty(value = "gradeDistributionInfo")
+    private CollegeAndSchoolGradeDistributionResult gradeDistributionInfo;
+
+    @ApiModelProperty(value = "dimensionInfo")
+    private DimensionAnalyzeResult dimensionInfo;
+
+    @ApiModelProperty(value = "answerInfo")
+    private QuestionInfoResult answerInfo;
+
+    @ApiModelProperty(value = "teacherInfo")
+    private TeacherInfoListResult teacherInfo;
+
+    @ApiModelProperty(value = "questionInfo")
+    private QuestionListResult questionInfo;
+
+    public CollegeAndCourseResult() {
+
+    }
+
+    public CollegeAndCourseResult(CourseInfoResult courseInfo, CollegeAndSchoolGradeDistributionResult gradeDistributionInfo,
+                                  DimensionAnalyzeResult dimensionInfo, QuestionInfoResult answerInfo, TeacherInfoListResult
+                                          teacherInfo, QuestionListResult questionInfo) {
+        this.courseInfo = courseInfo;
+        this.gradeDistributionInfo = gradeDistributionInfo;
+        this.dimensionInfo = dimensionInfo;
+        this.answerInfo = answerInfo;
+        this.teacherInfo = teacherInfo;
+        this.questionInfo = questionInfo;
+    }
+
+    public CourseInfoResult getCourseInfo() {
+        return courseInfo;
+    }
+
+    public void setCourseInfo(CourseInfoResult courseInfo) {
+        this.courseInfo = courseInfo;
+    }
+
+    public CollegeAndSchoolGradeDistributionResult getGradeDistributionInfo() {
+        return gradeDistributionInfo;
+    }
+
+    public void setGradeDistributionInfo(CollegeAndSchoolGradeDistributionResult gradeDistributionInfo) {
+        this.gradeDistributionInfo = gradeDistributionInfo;
+    }
+
+    public DimensionAnalyzeResult getDimensionInfo() {
+        return dimensionInfo;
+    }
+
+    public void setDimensionInfo(DimensionAnalyzeResult dimensionInfo) {
+        this.dimensionInfo = dimensionInfo;
+    }
+
+    public QuestionInfoResult getAnswerInfo() {
+        return answerInfo;
+    }
+
+    public void setAnswerInfo(QuestionInfoResult answerInfo) {
+        this.answerInfo = answerInfo;
+    }
+
+    public TeacherInfoListResult getTeacherInfo() {
+        return teacherInfo;
+    }
+
+    public void setTeacherInfo(TeacherInfoListResult teacherInfo) {
+        this.teacherInfo = teacherInfo;
+    }
+
+    public QuestionListResult getQuestionInfo() {
+        return questionInfo;
+    }
+
+    public void setQuestionInfo(QuestionListResult questionInfo) {
+        this.questionInfo = questionInfo;
+    }
+}

+ 47 - 0
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/CollegeAndSchoolGradeDistributionResult.java

@@ -0,0 +1,47 @@
+package com.qmth.teachcloud.report.business.bean.result;
+
+import io.swagger.annotations.ApiModelProperty;
+
+import java.io.Serializable;
+import java.util.List;
+
+/**
+ * @Description: 学院和学校百分比
+ * @Param:
+ * @return:
+ * @Author: wangliang
+ * @Date: 2021/6/10
+ */
+public class CollegeAndSchoolGradeDistributionResult implements Serializable {
+
+    @ApiModelProperty(value = "分数段等级list")
+    private List<GradeDistributionResult> gradeDistributionList;
+
+    @ApiModelProperty(value = "分数段等级list")
+    private List<PiecewiseDistributionResult> piecewiseDistributionList;
+
+    public CollegeAndSchoolGradeDistributionResult() {
+
+    }
+
+    public CollegeAndSchoolGradeDistributionResult(List<GradeDistributionResult> gradeDistributionList, List<PiecewiseDistributionResult> piecewiseDistributionList) {
+        this.gradeDistributionList = gradeDistributionList;
+        this.piecewiseDistributionList = piecewiseDistributionList;
+    }
+
+    public List<GradeDistributionResult> getGradeDistributionList() {
+        return gradeDistributionList;
+    }
+
+    public void setGradeDistributionList(List<GradeDistributionResult> gradeDistributionList) {
+        this.gradeDistributionList = gradeDistributionList;
+    }
+
+    public List<PiecewiseDistributionResult> getPiecewiseDistributionList() {
+        return piecewiseDistributionList;
+    }
+
+    public void setPiecewiseDistributionList(List<PiecewiseDistributionResult> piecewiseDistributionList) {
+        this.piecewiseDistributionList = piecewiseDistributionList;
+    }
+}

+ 6 - 6
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/CourseDimensionResult.java

@@ -44,10 +44,10 @@ public class CourseDimensionResult implements Serializable {
     private Integer totalCount;
 
     @ApiModelProperty(value = "学校比率")
-    private BigDecimal schScoreRate;
+    private Double schScoreRate;
 
     @ApiModelProperty(value = "学院比率")
-    private BigDecimal colScoreRate;
+    private Double colScoreRate;
 
     @ApiModelProperty(value = "学院名称")
     private String collegeName;
@@ -116,19 +116,19 @@ public class CourseDimensionResult implements Serializable {
         this.totalCount = totalCount;
     }
 
-    public BigDecimal getSchScoreRate() {
+    public Double getSchScoreRate() {
         return schScoreRate;
     }
 
-    public void setSchScoreRate(BigDecimal schScoreRate) {
+    public void setSchScoreRate(Double schScoreRate) {
         this.schScoreRate = schScoreRate;
     }
 
-    public BigDecimal getColScoreRate() {
+    public Double getColScoreRate() {
         return colScoreRate;
     }
 
-    public void setColScoreRate(BigDecimal colScoreRate) {
+    public void setColScoreRate(Double colScoreRate) {
         this.colScoreRate = colScoreRate;
     }
 

+ 35 - 0
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/DimensionAnalyzeResult.java

@@ -0,0 +1,35 @@
+package com.qmth.teachcloud.report.business.bean.result;
+
+import io.swagger.annotations.ApiModelProperty;
+
+import java.io.Serializable;
+import java.util.List;
+
+/**
+ * @Description: DimensionAnalyzeResult
+ * @Param:
+ * @return:
+ * @Author: wangliang
+ * @Date: 2021/6/10
+ */
+public class DimensionAnalyzeResult implements Serializable {
+
+    @ApiModelProperty(value = "dimensionAnalyzeList")
+    private List<ModuleDimensionResult> dimensionAnalyzeList;
+
+    public DimensionAnalyzeResult() {
+
+    }
+
+    public DimensionAnalyzeResult(List<ModuleDimensionResult> dimensionAnalyzeList) {
+        this.dimensionAnalyzeList = dimensionAnalyzeList;
+    }
+
+    public List<ModuleDimensionResult> getDimensionAnalyzeList() {
+        return dimensionAnalyzeList;
+    }
+
+    public void setDimensionAnalyzeList(List<ModuleDimensionResult> dimensionAnalyzeList) {
+        this.dimensionAnalyzeList = dimensionAnalyzeList;
+    }
+}

+ 89 - 0
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/DimensionInfoResult.java

@@ -0,0 +1,89 @@
+package com.qmth.teachcloud.report.business.bean.result;
+
+import com.fasterxml.jackson.annotation.JsonInclude;
+import io.swagger.annotations.ApiModelProperty;
+
+import java.io.Serializable;
+
+/**
+ * @Description: 维度info result
+ * @Param:
+ * @return:
+ * @Author: wangliang
+ * @Date: 2021/6/10
+ */
+@JsonInclude(JsonInclude.Include.NON_NULL)
+public class DimensionInfoResult implements Serializable {
+
+    @ApiModelProperty(value = "维度编码")
+    private String dimensionCode;
+
+    @ApiModelProperty(value = "维度名称")
+    private String dimensionName;
+
+    @ApiModelProperty(value = "统计")
+    private String totalCount;
+
+    @ApiModelProperty(value = "学校得分率")
+    private String schScoreRate;
+
+    @ApiModelProperty(value = "学院得分率")
+    private String colScoreRate;
+
+    public DimensionInfoResult() {
+
+    }
+
+    public DimensionInfoResult(String dimensionCode, String dimensionName, String totalCount, String schScoreRate, String colScoreRate) {
+        this.dimensionCode = dimensionCode;
+        this.dimensionName = dimensionName;
+        this.totalCount = totalCount;
+        this.schScoreRate = schScoreRate;
+        this.colScoreRate = colScoreRate;
+    }
+
+    public DimensionInfoResult(String dimensionCode, String dimensionName) {
+        this.dimensionCode = dimensionCode;
+        this.dimensionName = dimensionName;
+    }
+
+    public String getDimensionCode() {
+        return dimensionCode;
+    }
+
+    public void setDimensionCode(String dimensionCode) {
+        this.dimensionCode = dimensionCode;
+    }
+
+    public String getDimensionName() {
+        return dimensionName;
+    }
+
+    public void setDimensionName(String dimensionName) {
+        this.dimensionName = dimensionName;
+    }
+
+    public String getTotalCount() {
+        return totalCount;
+    }
+
+    public void setTotalCount(String totalCount) {
+        this.totalCount = totalCount;
+    }
+
+    public String getSchScoreRate() {
+        return schScoreRate;
+    }
+
+    public void setSchScoreRate(String schScoreRate) {
+        this.schScoreRate = schScoreRate;
+    }
+
+    public String getColScoreRate() {
+        return colScoreRate;
+    }
+
+    public void setColScoreRate(String colScoreRate) {
+        this.colScoreRate = colScoreRate;
+    }
+}

+ 20 - 6
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/ExamRecordResult.java

@@ -1,5 +1,7 @@
 package com.qmth.teachcloud.report.business.bean.result;
 
+import com.fasterxml.jackson.databind.annotation.JsonSerialize;
+import com.fasterxml.jackson.databind.ser.std.ToStringSerializer;
 import io.swagger.annotations.ApiModelProperty;
 
 import java.io.Serializable;
@@ -20,11 +22,23 @@ public class ExamRecordResult implements Serializable {
     @ApiModelProperty(value = "学院名称")
     private String collegeName;
 
+    @ApiModelProperty(value = "学院id")
+    @JsonSerialize(using = ToStringSerializer.class)
+    private Long collegeId;
+
     @ApiModelProperty(value = "赋分分数")
-    private BigDecimal assignedScore;
+    private Double assignedScore;
 
     @ApiModelProperty(value = "百分位等级")
-    private BigDecimal percentGrade;
+    private Double percentGrade;
+
+    public Long getCollegeId() {
+        return collegeId;
+    }
+
+    public void setCollegeId(Long collegeId) {
+        this.collegeId = collegeId;
+    }
 
     public String getTicketNumber() {
         return ticketNumber;
@@ -42,19 +56,19 @@ public class ExamRecordResult implements Serializable {
         this.collegeName = collegeName;
     }
 
-    public BigDecimal getAssignedScore() {
+    public Double getAssignedScore() {
         return assignedScore;
     }
 
-    public void setAssignedScore(BigDecimal assignedScore) {
+    public void setAssignedScore(Double assignedScore) {
         this.assignedScore = assignedScore;
     }
 
-    public BigDecimal getPercentGrade() {
+    public Double getPercentGrade() {
         return percentGrade;
     }
 
-    public void setPercentGrade(BigDecimal percentGrade) {
+    public void setPercentGrade(Double percentGrade) {
         this.percentGrade = percentGrade;
     }
 }

+ 58 - 0
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/GradeDistributionResult.java

@@ -0,0 +1,58 @@
+package com.qmth.teachcloud.report.business.bean.result;
+
+import io.swagger.annotations.ApiModelProperty;
+
+import java.io.Serializable;
+
+/**
+ * @Description: 百分位result
+ * @Param:
+ * @return:
+ * @Author: wangliang
+ * @Date: 2021/6/10
+ */
+public class GradeDistributionResult implements Serializable {
+
+    @ApiModelProperty(value = "学院人数")
+    private Double colCount;
+
+    @ApiModelProperty(value = "学校人数")
+    private Double schCount;
+
+    @ApiModelProperty(value = "描述")
+    private String describe;
+
+    public GradeDistributionResult() {
+
+    }
+
+    public GradeDistributionResult(Double colCount, Double schCount, String describe) {
+        this.colCount = colCount;
+        this.schCount = schCount;
+        this.describe = describe;
+    }
+
+    public Double getColCount() {
+        return colCount;
+    }
+
+    public void setColCount(Double colCount) {
+        this.colCount = colCount;
+    }
+
+    public Double getSchCount() {
+        return schCount;
+    }
+
+    public void setSchCount(Double schCount) {
+        this.schCount = schCount;
+    }
+
+    public String getDescribe() {
+        return describe;
+    }
+
+    public void setDescribe(String describe) {
+        this.describe = describe;
+    }
+}

+ 71 - 0
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/ModuleDimensionResult.java

@@ -0,0 +1,71 @@
+package com.qmth.teachcloud.report.business.bean.result;
+
+import io.swagger.annotations.ApiModelProperty;
+
+import java.io.Serializable;
+import java.util.List;
+
+/**
+ * @Description: ModuleDimensionResult
+ * @Param:
+ * @return:
+ * @Author: wangliang
+ * @Date: 2021/6/10
+ */
+public class ModuleDimensionResult implements Serializable {
+
+    @ApiModelProperty(value = "模块名称")
+    private String moduleName;
+
+    @ApiModelProperty(value = "dioList")
+    private List<DimensionInfoResult> dioList;
+
+    @ApiModelProperty(value = "batterThanAll")
+    private List<DimensionInfoResult> batterThanAll;
+
+    @ApiModelProperty(value = "worseThanAll")
+    private List<DimensionInfoResult> worseThanAll;
+
+    public ModuleDimensionResult() {
+
+    }
+
+    public ModuleDimensionResult(String moduleName, List<DimensionInfoResult> dioList, List<DimensionInfoResult> batterThanAll, List<DimensionInfoResult> worseThanAll) {
+        this.moduleName = moduleName;
+        this.dioList = dioList;
+        this.batterThanAll = batterThanAll;
+        this.worseThanAll = worseThanAll;
+    }
+
+    public String getModuleName() {
+        return moduleName;
+    }
+
+    public void setModuleName(String moduleName) {
+        this.moduleName = moduleName;
+    }
+
+    public List<DimensionInfoResult> getDioList() {
+        return dioList;
+    }
+
+    public void setDioList(List<DimensionInfoResult> dioList) {
+        this.dioList = dioList;
+    }
+
+    public List<DimensionInfoResult> getBatterThanAll() {
+        return batterThanAll;
+    }
+
+    public void setBatterThanAll(List<DimensionInfoResult> batterThanAll) {
+        this.batterThanAll = batterThanAll;
+    }
+
+    public List<DimensionInfoResult> getWorseThanAll() {
+        return worseThanAll;
+    }
+
+    public void setWorseThanAll(List<DimensionInfoResult> worseThanAll) {
+        this.worseThanAll = worseThanAll;
+    }
+}

+ 47 - 0
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/PaperTypeResult.java

@@ -0,0 +1,47 @@
+package com.qmth.teachcloud.report.business.bean.result;
+
+import io.swagger.annotations.ApiModelProperty;
+
+import java.io.Serializable;
+import java.util.List;
+
+/**
+ * @Description: PaperTypeResult
+ * @Param:
+ * @return:
+ * @Author: wangliang
+ * @Date: 2021/6/11
+ */
+public class PaperTypeResult implements Serializable {
+
+    @ApiModelProperty(value = "卷型")
+    private String paperType;
+
+    @ApiModelProperty(value = "cellList")
+    private List<CellResult> cellList;
+
+    public PaperTypeResult() {
+
+    }
+
+    public PaperTypeResult(String paperType, List<CellResult> cellList) {
+        this.paperType = paperType;
+        this.cellList = cellList;
+    }
+
+    public String getPaperType() {
+        return paperType;
+    }
+
+    public void setPaperType(String paperType) {
+        this.paperType = paperType;
+    }
+
+    public List<CellResult> getCellList() {
+        return cellList;
+    }
+
+    public void setCellList(List<CellResult> cellList) {
+        this.cellList = cellList;
+    }
+}

+ 94 - 0
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/PiecewiseDistributionResult.java

@@ -0,0 +1,94 @@
+package com.qmth.teachcloud.report.business.bean.result;
+
+import io.swagger.annotations.ApiModelProperty;
+
+import java.io.Serializable;
+
+/**
+ * @Description: 分数段result
+ * @Param:
+ * @return:
+ * @Author: wangliang
+ * @Date: 2021/6/10
+ */
+public class PiecewiseDistributionResult implements Serializable {
+
+    @ApiModelProperty(value = "名称")
+    private String name;
+
+    @ApiModelProperty(value = "学院人数")
+    private Double colCount;
+
+    @ApiModelProperty(value = "学院人数比率")
+    private Double colCountRate;
+
+    @ApiModelProperty(value = "学校人数")
+    private Double schCount;
+
+    @ApiModelProperty(value = "学校人数比率")
+    private Double schCountRate;
+
+    @ApiModelProperty(value = "备注")
+    private String remark;
+
+    public PiecewiseDistributionResult() {
+
+    }
+
+    public PiecewiseDistributionResult(String name, Double colCount, Double colCountRate, Double schCount, Double schCountRate, String remark) {
+        this.name = name;
+        this.colCount = colCount;
+        this.colCountRate = colCountRate;
+        this.schCount = schCount;
+        this.schCountRate = schCountRate;
+        this.remark = remark;
+    }
+
+    public String getName() {
+        return name;
+    }
+
+    public void setName(String name) {
+        this.name = name;
+    }
+
+    public Double getColCount() {
+        return colCount;
+    }
+
+    public void setColCount(Double colCount) {
+        this.colCount = colCount;
+    }
+
+    public Double getColCountRate() {
+        return colCountRate;
+    }
+
+    public void setColCountRate(Double colCountRate) {
+        this.colCountRate = colCountRate;
+    }
+
+    public Double getSchCount() {
+        return schCount;
+    }
+
+    public void setSchCount(Double schCount) {
+        this.schCount = schCount;
+    }
+
+    public Double getSchCountRate() {
+        return schCountRate;
+    }
+
+    public void setSchCountRate(Double schCountRate) {
+        this.schCountRate = schCountRate;
+    }
+
+    public String getRemark() {
+        return remark;
+    }
+
+    public void setRemark(String remark) {
+        this.remark = remark;
+    }
+}

+ 35 - 0
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/QuestionInfoResult.java

@@ -0,0 +1,35 @@
+package com.qmth.teachcloud.report.business.bean.result;
+
+import io.swagger.annotations.ApiModelProperty;
+
+import java.io.Serializable;
+import java.util.List;
+
+/**
+ * @Description: QuestionInfoResult
+ * @Param:
+ * @return:
+ * @Author: wangliang
+ * @Date: 2021/6/11
+ */
+public class QuestionInfoResult implements Serializable {
+
+    @ApiModelProperty(value = "questionInfoList")
+    private List<PaperTypeResult> questionInfoList;
+
+    public QuestionInfoResult() {
+
+    }
+
+    public QuestionInfoResult(List<PaperTypeResult> questionInfoList) {
+        this.questionInfoList = questionInfoList;
+    }
+
+    public List<PaperTypeResult> getQuestionInfoList() {
+        return questionInfoList;
+    }
+
+    public void setQuestionInfoList(List<PaperTypeResult> questionInfoList) {
+        this.questionInfoList = questionInfoList;
+    }
+}

+ 35 - 0
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/QuestionListResult.java

@@ -0,0 +1,35 @@
+package com.qmth.teachcloud.report.business.bean.result;
+
+import io.swagger.annotations.ApiModelProperty;
+
+import java.io.Serializable;
+import java.util.List;
+
+/**
+ * @Description: QuestionListResult
+ * @Param:
+ * @return:
+ * @Author: wangliang
+ * @Date: 2021/6/11
+ */
+public class QuestionListResult implements Serializable {
+
+    @ApiModelProperty(value = "questionList")
+    private List<QuestionResult> questionList;
+
+    public QuestionListResult() {
+
+    }
+
+    public QuestionListResult(List<QuestionResult> questionList) {
+        this.questionList = questionList;
+    }
+
+    public List<QuestionResult> getQuestionList() {
+        return questionList;
+    }
+
+    public void setQuestionList(List<QuestionResult> questionList) {
+        this.questionList = questionList;
+    }
+}

+ 59 - 0
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/QuestionResult.java

@@ -0,0 +1,59 @@
+package com.qmth.teachcloud.report.business.bean.result;
+
+import io.swagger.annotations.ApiModelProperty;
+
+import java.io.Serializable;
+import java.util.List;
+
+/**
+ * @Description: QuestionResult
+ * @Param:
+ * @return:
+ * @Author: wangliang
+ * @Date: 2021/6/11
+ */
+public class QuestionResult implements Serializable {
+
+    @ApiModelProperty(value = "试卷类型")
+    private String paperType;
+
+    @ApiModelProperty(value = "cellList")
+    private List<TBPaperStructResult> cellList;
+
+    @ApiModelProperty(value = "dimensionList")
+    private List<DimensionInfoResult> dimensionList;
+
+    public QuestionResult() {
+
+    }
+
+    public QuestionResult(String paperType, List<TBPaperStructResult> cellList, List<DimensionInfoResult> dimensionList) {
+        this.paperType = paperType;
+        this.cellList = cellList;
+        this.dimensionList = dimensionList;
+    }
+
+    public String getPaperType() {
+        return paperType;
+    }
+
+    public void setPaperType(String paperType) {
+        this.paperType = paperType;
+    }
+
+    public List<TBPaperStructResult> getCellList() {
+        return cellList;
+    }
+
+    public void setCellList(List<TBPaperStructResult> cellList) {
+        this.cellList = cellList;
+    }
+
+    public List<DimensionInfoResult> getDimensionList() {
+        return dimensionList;
+    }
+
+    public void setDimensionList(List<DimensionInfoResult> dimensionList) {
+        this.dimensionList = dimensionList;
+    }
+}

+ 17 - 3
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/TBAnswerResult.java

@@ -1,5 +1,7 @@
 package com.qmth.teachcloud.report.business.bean.result;
 
+import com.fasterxml.jackson.databind.annotation.JsonSerialize;
+import com.fasterxml.jackson.databind.ser.std.ToStringSerializer;
 import io.swagger.annotations.ApiModelProperty;
 
 import java.io.Serializable;
@@ -18,7 +20,7 @@ public class TBAnswerResult implements Serializable {
     private String paperType;
 
     @ApiModelProperty(value = "得分率")
-    private BigDecimal scoreRate;
+    private Double scoreRate;
 
     @ApiModelProperty(value = "难度")
     private String difficult;
@@ -26,6 +28,18 @@ public class TBAnswerResult implements Serializable {
     @ApiModelProperty(value = "学院名称")
     private String collegeName;
 
+    @ApiModelProperty(value = "学院名称")
+    @JsonSerialize(using = ToStringSerializer.class)
+    private Long collegeId;
+
+    public Long getCollegeId() {
+        return collegeId;
+    }
+
+    public void setCollegeId(Long collegeId) {
+        this.collegeId = collegeId;
+    }
+
     public String getPaperType() {
         return paperType;
     }
@@ -34,11 +48,11 @@ public class TBAnswerResult implements Serializable {
         this.paperType = paperType;
     }
 
-    public BigDecimal getScoreRate() {
+    public Double getScoreRate() {
         return scoreRate;
     }
 
-    public void setScoreRate(BigDecimal scoreRate) {
+    public void setScoreRate(Double scoreRate) {
         this.scoreRate = scoreRate;
     }
 

+ 35 - 0
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/bean/result/TeacherInfoListResult.java

@@ -0,0 +1,35 @@
+package com.qmth.teachcloud.report.business.bean.result;
+
+import io.swagger.annotations.ApiModelProperty;
+
+import java.io.Serializable;
+import java.util.List;
+
+/**
+ * @Description: TeacherInfoListResult
+ * @Param:
+ * @return:
+ * @Author: wangliang
+ * @Date: 2021/6/11
+ */
+public class TeacherInfoListResult implements Serializable {
+
+    @ApiModelProperty(value = "简介")
+    List<TAExamCourseTeacherResult> teacherInfoList;
+
+    public TeacherInfoListResult() {
+
+    }
+
+    public TeacherInfoListResult(List<TAExamCourseTeacherResult> teacherInfoList) {
+        this.teacherInfoList = teacherInfoList;
+    }
+
+    public List<TAExamCourseTeacherResult> getTeacherInfoList() {
+        return teacherInfoList;
+    }
+
+    public void setTeacherInfoList(List<TAExamCourseTeacherResult> teacherInfoList) {
+        this.teacherInfoList = teacherInfoList;
+    }
+}

+ 13 - 0
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/entity/TAExamCourseRecordDio.java

@@ -60,6 +60,11 @@ public class TAExamCourseRecordDio implements Serializable {
     @TableField(value = "course_name")
     private String courseName;
 
+    @ApiModelProperty(value = "学生id")
+    @JsonSerialize(using = ToStringSerializer.class)
+    @TableField(value = "student_id")
+    private Long studentId;
+
     @ApiModelProperty(value = "考号")
     @TableField(value = "student_code")
     private String studentCode;
@@ -212,4 +217,12 @@ public class TAExamCourseRecordDio implements Serializable {
     public void setSchoolId(Long schoolId) {
         this.schoolId = schoolId;
     }
+
+    public Long getStudentId() {
+        return studentId;
+    }
+
+    public void setStudentId(Long studentId) {
+        this.studentId = studentId;
+    }
 }

+ 13 - 0
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/entity/TAExamCourseRecordMod.java

@@ -56,6 +56,11 @@ public class TAExamCourseRecordMod implements Serializable {
     @TableField(value = "course_name")
     private String courseName;
 
+    @ApiModelProperty(value = "考生id")
+    @JsonSerialize(using = ToStringSerializer.class)
+    @TableField(value = "student_id")
+    private Long studentId;
+
     @ApiModelProperty(value = "考号")
     @TableField(value = "student_code")
     private String studentCode;
@@ -248,4 +253,12 @@ public class TAExamCourseRecordMod implements Serializable {
     public void setStudentCode(String studentCode) {
         this.studentCode = studentCode;
     }
+
+    public Long getStudentId() {
+        return studentId;
+    }
+
+    public void setStudentId(Long studentId) {
+        this.studentId = studentId;
+    }
 }

+ 173 - 28
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/entity/TAPaperStruct.java

@@ -51,6 +51,55 @@ public class TAPaperStruct implements Serializable {
     @TableField(value = "course_name")
     private String courseName;
 
+    @ApiModelProperty(value = "基础试卷id(冗余)")
+    @JsonSerialize(using = ToStringSerializer.class)
+    @TableField(value = "paper_id")
+    private Long paperId;
+
+    @ApiModelProperty(value = "大题名称")
+    @TableField(value = "question_name")
+    private String questionName;
+
+    @ApiModelProperty(value = "题号类型(客观题、主观题)")
+    @TableField(value = "number_type")
+    private String numberType;
+
+    @ApiModelProperty(value = "大题号")
+    @TableField(value = "big_question_number")
+    private String bigQuestionNumber;
+
+    @ApiModelProperty(value = "小题号(每一课程试卷的唯一标识)")
+    @TableField(value = "small_question_number")
+    private String smallQuestionNumber;
+
+    @ApiModelProperty(value = "题目类型")
+    @TableField(value = "question_type")
+    private String questionType;
+
+    @ApiModelProperty(value = "满分")
+    @TableField(value = "full_score")
+    private BigDecimal fullScore;
+
+    @ApiModelProperty(value = "计分规则")
+    @TableField(value = "score_rules")
+    private String scoreRules;
+
+    @ApiModelProperty(value = "规则说明")
+    @TableField(value = "rules_desc")
+    private String rulesDesc;
+
+    @ApiModelProperty(value = "知识维度")
+    @TableField(value = "knowledge_dimension")
+    private String knowledgeDimension;
+
+    @ApiModelProperty(value = "能力维度")
+    @TableField(value = "ability_dimension")
+    private String abilityDimension;
+
+    @ApiModelProperty(value = "素养维度")
+    @TableField(value = "literacy_dimension")
+    private String literacyDimension;
+
     @ApiModelProperty(value = "得分率")
     @TableField(value = "score_rate")
     private BigDecimal scoreRate;
@@ -83,30 +132,6 @@ public class TAPaperStruct implements Serializable {
         this.paperStructId = paperStructId;
     }
 
-    public BigDecimal getScoreRate() {
-        return scoreRate;
-    }
-
-    public void setScoreRate(BigDecimal scoreRate) {
-        this.scoreRate = scoreRate;
-    }
-
-    public String getDifficult() {
-        return difficult;
-    }
-
-    public void setDifficult(String difficult) {
-        this.difficult = difficult;
-    }
-
-    public BigDecimal getValidity() {
-        return validity;
-    }
-
-    public void setValidity(BigDecimal validity) {
-        this.validity = validity;
-    }
-
     public Long getExamId() {
         return examId;
     }
@@ -115,6 +140,14 @@ public class TAPaperStruct implements Serializable {
         this.examId = examId;
     }
 
+    public Long getSchoolId() {
+        return schoolId;
+    }
+
+    public void setSchoolId(Long schoolId) {
+        this.schoolId = schoolId;
+    }
+
     public String getCourseCode() {
         return courseCode;
     }
@@ -131,11 +164,123 @@ public class TAPaperStruct implements Serializable {
         this.courseName = courseName;
     }
 
-    public Long getSchoolId() {
-        return schoolId;
+    public Long getPaperId() {
+        return paperId;
     }
 
-    public void setSchoolId(Long schoolId) {
-        this.schoolId = schoolId;
+    public void setPaperId(Long paperId) {
+        this.paperId = paperId;
+    }
+
+    public String getQuestionName() {
+        return questionName;
+    }
+
+    public void setQuestionName(String questionName) {
+        this.questionName = questionName;
+    }
+
+    public String getNumberType() {
+        return numberType;
+    }
+
+    public void setNumberType(String numberType) {
+        this.numberType = numberType;
+    }
+
+    public String getBigQuestionNumber() {
+        return bigQuestionNumber;
+    }
+
+    public void setBigQuestionNumber(String bigQuestionNumber) {
+        this.bigQuestionNumber = bigQuestionNumber;
+    }
+
+    public String getSmallQuestionNumber() {
+        return smallQuestionNumber;
+    }
+
+    public void setSmallQuestionNumber(String smallQuestionNumber) {
+        this.smallQuestionNumber = smallQuestionNumber;
+    }
+
+    public String getQuestionType() {
+        return questionType;
+    }
+
+    public void setQuestionType(String questionType) {
+        this.questionType = questionType;
+    }
+
+    public BigDecimal getFullScore() {
+        return fullScore;
+    }
+
+    public void setFullScore(BigDecimal fullScore) {
+        this.fullScore = fullScore;
+    }
+
+    public String getScoreRules() {
+        return scoreRules;
+    }
+
+    public void setScoreRules(String scoreRules) {
+        this.scoreRules = scoreRules;
+    }
+
+    public String getRulesDesc() {
+        return rulesDesc;
+    }
+
+    public void setRulesDesc(String rulesDesc) {
+        this.rulesDesc = rulesDesc;
+    }
+
+    public String getKnowledgeDimension() {
+        return knowledgeDimension;
+    }
+
+    public void setKnowledgeDimension(String knowledgeDimension) {
+        this.knowledgeDimension = knowledgeDimension;
+    }
+
+    public String getAbilityDimension() {
+        return abilityDimension;
+    }
+
+    public void setAbilityDimension(String abilityDimension) {
+        this.abilityDimension = abilityDimension;
+    }
+
+    public String getLiteracyDimension() {
+        return literacyDimension;
+    }
+
+    public void setLiteracyDimension(String literacyDimension) {
+        this.literacyDimension = literacyDimension;
+    }
+
+    public BigDecimal getScoreRate() {
+        return scoreRate;
+    }
+
+    public void setScoreRate(BigDecimal scoreRate) {
+        this.scoreRate = scoreRate;
+    }
+
+    public String getDifficult() {
+        return difficult;
+    }
+
+    public void setDifficult(String difficult) {
+        this.difficult = difficult;
+    }
+
+    public BigDecimal getValidity() {
+        return validity;
+    }
+
+    public void setValidity(BigDecimal validity) {
+        this.validity = validity;
     }
 }

+ 33 - 0
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/enums/GradeScopeEnum.java

@@ -0,0 +1,33 @@
+package com.qmth.teachcloud.report.business.enums;
+
+/**
+ * @Description: 百分位登记enum
+ * @Param:
+ * @return:
+ * @Author: wangliang
+ * @Date: 2021/6/10
+ */
+public enum GradeScopeEnum {
+    LOW_THAN_SIXTY("[0,60)", "60以下"),
+    SIXTY_TO_SEVENTY("[60,70)", "60-70"),
+    SEVENTY_TO_EIGHTY("[70,80)", "70-80"),
+    EIGHTY_TO_NINETY("[80,90)", "80-90"),
+    NINETY_TO_NINETY_FIVE("[90,95)", "90-95"),
+    NINETY_FIVE_TO_ONE_HUNDRED("[95,100)", "95-100");
+
+    GradeScopeEnum(String scope, String describe) {
+        this.scope = scope;
+        this.describe = describe;
+    }
+
+    private final String scope;
+    private final String describe;
+
+    public String getScope() {
+        return scope;
+    }
+
+    public String getDescribe() {
+        return describe;
+    }
+}

+ 38 - 0
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/enums/PiecewiseScopeEnum.java

@@ -0,0 +1,38 @@
+package com.qmth.teachcloud.report.business.enums;
+
+/**
+ * @Description: 分数段登记
+ * @Param:
+ * @return:
+ * @Author: wangliang
+ * @Date: 2021/6/10
+ */
+public enum PiecewiseScopeEnum {
+    TOP_10("[90,100)", "TOP10", "全体百分等级大于等于10的人数比例"),
+    HIGH_SUB_LEVEL("[75,100)", "高分段", "全体百分等级大于等于75的人数比例,包含TOP10;"),
+    Good("[50,75)", "良好", "百分等级小于75,大于等于50的人数比例;"),
+    MEDIUM("[25,50)", "中等", "全体百分等级小于50,大于等于25的人数比例;"),
+    LOW_SUB_LEVEL("[0,25)", "低分段", "全体百分等级低于25的人数比例;");
+
+    PiecewiseScopeEnum(String scope, String name, String remark) {
+        this.scope = scope;
+        this.name = name;
+        this.remark = remark;
+    }
+
+    private final String scope;
+    private final String name;
+    private final String remark;
+
+    public String getScope() {
+        return scope;
+    }
+
+    public String getName() {
+        return name;
+    }
+
+    public String getRemark() {
+        return remark;
+    }
+}

+ 11 - 0
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/mapper/TBAnswerMapper.java

@@ -1,12 +1,14 @@
 package com.qmth.teachcloud.report.business.mapper;
 
 import com.baomidou.mybatisplus.core.mapper.BaseMapper;
+import com.qmth.teachcloud.report.business.bean.dto.AnswerDetailBean;
 import com.qmth.teachcloud.report.business.bean.dto.query.BasicAnswerDto;
 import com.qmth.teachcloud.report.business.bean.dto.query.ValidAnswerDetailDto;
 import com.qmth.teachcloud.report.business.bean.result.TBAnswerResult;
 import com.qmth.teachcloud.report.business.entity.TBAnswer;
 import org.apache.ibatis.annotations.Param;
 
+import java.util.LinkedList;
 import java.util.List;
 
 /**
@@ -44,4 +46,13 @@ public interface TBAnswerMapper extends BaseMapper<TBAnswer> {
      * @return
      */
     List<TBAnswerResult> findValidAnswerDetail(@Param("examId") Long examId, @Param("courseCode") String courseCode);
+
+    /**
+     * 查找实际参加考试的详细作答记录
+     *
+     * @param examId  考试id
+     * @param courseCode  课程编号
+     * @return 键值对
+     */
+    LinkedList<AnswerDetailBean> findValidAnswerDetailWithPap(@Param("examId") Long examId, @Param("courseCode") String courseCode);
 }

+ 49 - 20
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/service/AnalyzeForStudentService.java → teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/service/AnalyzeForReportService.java

@@ -5,40 +5,45 @@ package com.qmth.teachcloud.report.business.service;
  * @Author: CaoZixuan
  * @Date: 2021-06-06
  */
-public interface AnalyzeForStudentService {
+public interface AnalyzeForReportService {
 
     /**
      * 构建考试课程分析表 't_a_exam_course'
-     * @param examId 考试id
+     *
+     * @param examId     考试id
      * @param courseCode 课程编号
      * @return 结果
      */
-    String buildAnalyzeExamCourse(Long examId,String courseCode);
+    String buildAnalyzeExamCourse(Long examId, String courseCode);
+
     /**
      * 构建考试记录分析表数据 't_a_exam_course_record'
-     * @param examId 考试id
+     *
+     * @param examId     考试id
      * @param courseCode 课程编号
      * @return 结果
      */
-    String buildAnalyzeExamCourseRecord(Long examId,String courseCode);
+    String buildAnalyzeExamCourseRecord(Long examId, String courseCode);
 
     /**
      * 构建以考试课程-考察学院维度的分析表 't_a_exam_course_college_inspect'
-     * @param examId 考试id
+     *
+     * @param examId     考试id
      * @param courseCode 课程编号
      * @return 结果
      */
-    String buildAnalyzeExamCourseCollegeInspect(Long examId,String courseCode);
+    String buildAnalyzeExamCourseCollegeInspect(Long examId, String courseCode);
 
     // TODO: 2021/6/7 专业
 
     /**
      * 构建考试课程-班级维度的分析表 ’t_a_exam_course_clazz‘
-     * @param examId 考试id
+     *
+     * @param examId     考试id
      * @param courseCode 课程编号
      * @return 结果
      */
-    String buildAnalyzeExamCourseClazz(Long examId,String courseCode);
+    String buildAnalyzeExamCourseClazz(Long examId, String courseCode);
 
     /**
      * 分析计算某科目考试的所有考察点得分率并将计算结果插入't_a_exam_course_dio'和't_a_exam_course_record_dio'和‘t_a_exam_course_record_mod’表中
@@ -52,36 +57,49 @@ public interface AnalyzeForStudentService {
      * 2.获取该科目考试的试卷结构的数据信息
      * 3.获取该科目考试所有考察点的数据源
      * 4.获取该科目考试考生每题答题记录详情数据源
-     *
+     * <p>
      * 5.计算每个考察点所对应的题目集合
      * 6.计算每个考察点在此次考试所占分数
      * 7.计算每个考生各个知识点得分率并更新't_a_exam_course_record_dio'表
      * 8.计算此次考试各个考察点得分率并插入't_a_exam_course_dio'表
      * </p>
-     * @param examId 考试id
+     *
+     * @param examId     考试id
      * @param courseCode 课程编号
      * @return 结果
      */
-    String AnalyzePointScoreRate(Long examId,String courseCode) throws Exception;
+    String AnalyzePointScoreRate(Long examId, String courseCode) throws Exception;
 
     /**
      * 构建考试课程考察学院维度分析表
-     * @param examId 考试id
+     *
+     * @param examId     考试id
      * @param courseCode 课程编号
      * @return 结果
      */
-    String buildAnalyzeExamCourseCollegeInspectDio(Long examId,String courseCode);
+    String buildAnalyzeExamCourseCollegeInspectDio(Long examId, String courseCode);
 
     /**
      * 构建分析试卷结构表 't_a_paper_struct'表
-     * @param examId 考试id
+     *
+     * @param examId     考试id
      * @param courseCode 课程编号
      * @return 结果
      */
-    String buildAnalyzePaperStruct(Long examId,String courseCode);
+    String buildAnalyzePaperStruct(Long examId, String courseCode);
+
+    /**
+     * 构建科目题目难度分类得分率表
+     *
+     * @param examId     考试id
+     * @param courseCode 课程编号
+     * @return 结果
+     */
+    String buildExamPaperDifficult(Long examId, String courseCode);
 
     /**
      * 构建表 ‘t_a_exam_total’
+     *
      * @param examId 考试id
      * @return 结果
      */
@@ -89,17 +107,28 @@ public interface AnalyzeForStudentService {
 
     /**
      * 构建表 't_a_exam_course_college_teacher'
-     * @param examId 考试id
+     *
+     * @param examId     考试id
      * @param courseCode 课程编号
      * @return 结果
      */
-    String buildAnalyzeExamCourseCollegeTeacher(Long examId,String courseCode);
+    String buildAnalyzeExamCourseCollegeTeacher(Long examId, String courseCode);
 
     /**
      * 构建表 't_a_exam_course_teacher'
-     * @param examId 考试id
+     *
+     * @param examId     考试id
+     * @param courseCode 课程编号
+     * @return 结果
+     */
+    String buildAnalyzeExamCourseTeacher(Long examId, String courseCode);
+
+    /**
+     * 完成计算,更新表 't_b_exam_course'表 已计算
+     *
+     * @param examId     考试id
      * @param courseCode 课程编号
      * @return 结果
      */
-    String buildAnalyzeExamCourseTeacher(Long examId,String courseCode);
+    String finishCalculate(Long examId, String courseCode);
 }

+ 46 - 2
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/service/ReportCommonService.java

@@ -1,6 +1,8 @@
 package com.qmth.teachcloud.report.business.service;
 
-import com.qmth.teachcloud.report.business.bean.result.CourseInfoResult;
+import com.qmth.teachcloud.report.business.bean.result.*;
+
+import java.util.List;
 
 /**
  * @Description: 教研公共服务
@@ -29,5 +31,47 @@ public interface ReportCommonService {
      * @param collegeId
      * @return
      */
-    Object findCourseDistribution(Long examId, String courseCode, Long collegeId);
+    CollegeAndSchoolGradeDistributionResult findCourseDistribution(Long examId, String courseCode, Long collegeId);
+
+    /**
+     * 学院学科报表查询维度
+     *
+     * @param examId
+     * @param courseCode
+     * @param collegeId
+     * @return
+     */
+    DimensionAnalyzeResult findDimensionInfo(Long examId, String courseCode, Long collegeId);
+
+    /**
+     * 查找题目相关
+     *
+     * @param examId
+     * @param courseCode
+     * @param collegeId
+     * @param questionDatasource
+     * @return
+     */
+    QuestionInfoResult findSituationOfQuestions(Long examId, String courseCode, Long collegeId, List<TBPaperStructResult> questionDatasource);
+
+    /**
+     * 查找老师信息
+     *
+     * @param examId
+     * @param courseCode
+     * @param collegeId
+     * @return
+     */
+    TeacherInfoListResult findTeacherInfo(Long examId, String courseCode, Long collegeId);
+
+    /**
+     * 查找题目信息
+     *
+     * @param examId
+     * @param courseCode
+     * @param collegeId
+     * @param questionDatasource
+     * @return
+     */
+    QuestionListResult findQuestionInfo(Long examId, String courseCode, Long collegeId, List<TBPaperStructResult> questionDatasource);
 }

+ 2 - 2
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/service/TAExamCourseService.java

@@ -2,12 +2,12 @@ package com.qmth.teachcloud.report.business.service;
 
 import com.baomidou.mybatisplus.core.metadata.IPage;
 import com.baomidou.mybatisplus.extension.service.IService;
+import com.qmth.teachcloud.report.business.bean.result.CollegeAndCourseResult;
 import com.qmth.teachcloud.report.business.bean.result.TAExamCourseResult;
 import com.qmth.teachcloud.report.business.entity.TAExamCourse;
 import com.qmth.teachcloud.report.business.enums.PublishStatusEnum;
 import com.qmth.teachcloud.report.business.enums.SemesterEnum;
 
-import java.util.List;
 import java.util.Map;
 
 /**
@@ -57,5 +57,5 @@ public interface TAExamCourseService extends IService<TAExamCourse> {
      * @param schoolId
      * @return
      */
-    List<Object> surveyInspectAnalyseView(Long examId, SemesterEnum semester, String courseCode, Long schoolId);
+    CollegeAndCourseResult surveyInspectAnalyseView(Long examId, SemesterEnum semester, String courseCode, Long schoolId);
 }

+ 11 - 0
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/service/TBAnswerService.java

@@ -1,11 +1,13 @@
 package com.qmth.teachcloud.report.business.service;
 
 import com.baomidou.mybatisplus.extension.service.IService;
+import com.qmth.teachcloud.report.business.bean.dto.AnswerDetailBean;
 import com.qmth.teachcloud.report.business.bean.dto.query.BasicAnswerDto;
 import com.qmth.teachcloud.report.business.bean.dto.query.ValidAnswerDetailDto;
 import com.qmth.teachcloud.report.business.bean.result.TBAnswerResult;
 import com.qmth.teachcloud.report.business.entity.TBAnswer;
 
+import java.util.LinkedList;
 import java.util.List;
 
 /**
@@ -43,4 +45,13 @@ public interface TBAnswerService extends IService<TBAnswer> {
      * @return
      */
     List<TBAnswerResult> findValidAnswerDetail(Long examId, String courseCode);
+
+    /**
+     * 查找实际参加考试的详细作答记录
+     *
+     * @param examId  考试id
+     * @param courseCode  课程编号
+     * @return 键值对
+     */
+    LinkedList<AnswerDetailBean> findValidAnswerDetailWithPap(Long examId, String courseCode);
 }

+ 268 - 145
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/service/impl/AnalyzeForStudentServiceImpl.java → teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/service/impl/AnalyzeForReportServiceImpl.java

@@ -7,10 +7,12 @@ import com.qmth.teachcloud.common.enums.ExceptionResultEnum;
 import com.qmth.teachcloud.common.service.BasicCourseService;
 import com.qmth.teachcloud.common.service.SysOrgService;
 import com.qmth.teachcloud.common.service.SysUserService;
+import com.qmth.teachcloud.report.business.bean.dto.AnswerDetailBean;
 import com.qmth.teachcloud.report.business.bean.dto.query.BasicAnswerDto;
 import com.qmth.teachcloud.report.business.bean.dto.query.ValidAnswerDetailDto;
 import com.qmth.teachcloud.report.business.entity.*;
 import com.qmth.teachcloud.report.business.enums.LevelRuleEnum;
+import com.qmth.teachcloud.report.business.enums.PublishStatusEnum;
 import com.qmth.teachcloud.report.business.enums.QuantileEnum;
 import com.qmth.teachcloud.report.business.enums.ValidityEnum;
 import com.qmth.teachcloud.report.business.service.*;
@@ -34,7 +36,7 @@ import java.util.stream.Collectors;
  * @Date: 2021-06-06
  */
 @Service
-public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
+public class AnalyzeForReportServiceImpl implements AnalyzeForReportService {
     @Resource
     private TAExamCourseRecordService taExamCourseRecordService;
     @Resource
@@ -87,27 +89,29 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
     private TAExamCourseTeacherService taExamCourseTeacherService;
     @Resource
     private SysUserService sysUserService;
+    @Resource
+    private TAExamCourseDifficultService taExamCourseDifficultService;
 
 
     @Transactional(rollbackFor = Exception.class)
     @Override
     public String buildAnalyzeExamCourse(Long examId, String courseCode) {
-        List<String> effectiveCourseCodeList = tbExamCourseService.findEffectiveByExamId(examId,courseCode);
+        List<String> effectiveCourseCodeList = tbExamCourseService.findEffectiveByExamId(examId, courseCode);
         // 考试下考生作答数据源
         List<TAExamCourseRecord> dataSource = taExamCourseRecordService.list(new QueryWrapper<TAExamCourseRecord>().lambda()
-                .eq(TAExamCourseRecord::getExamId,examId));
+                .eq(TAExamCourseRecord::getExamId, examId));
         List<TAExamCourse> taExamCourseList = new ArrayList<>();
         // 有效的课程
         for (String effectiveCourseCode : effectiveCourseCodeList) {
             // 原数据删除
             taExamCourseService.remove(new QueryWrapper<TAExamCourse>().lambda()
-                    .eq(TAExamCourse::getExamId,examId)
-                    .eq(TAExamCourse::getCourseCode,effectiveCourseCode));
+                    .eq(TAExamCourse::getExamId, examId)
+                    .eq(TAExamCourse::getCourseCode, effectiveCourseCode));
 
             // TODO: 2021/6/7 查询试卷信息AB卷的准确方式(目前AB卷规则视为一致)
             List<TBPaper> tbPaperList = tbPaperService.list(new QueryWrapper<TBPaper>().lambda()
-                    .eq(TBPaper::getExamId,examId).eq(TBPaper::getCourseCode,effectiveCourseCode));
-            if (tbPaperList.size() < 1){
+                    .eq(TBPaper::getExamId, examId).eq(TBPaper::getCourseCode, effectiveCourseCode));
+            if (tbPaperList.size() < 1) {
                 throw ExceptionResultEnum.ERROR.exception("未找到试卷基础信息");
             }
             TBPaper tbPaper = tbPaperList.get(0);
@@ -127,7 +131,7 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
             int totalCount = totalDatasource.size();
             long realityCount = totalDatasource.stream().filter(e -> !e.getAbsent()).count();
             long absentCount = totalDatasource.stream().filter(TAExamCourseRecord::getAbsent).count();
-            if (totalCount != realityCount + absentCount){
+            if (totalCount != realityCount + absentCount) {
                 throw ExceptionResultEnum.ERROR.exception("考试人数数据异常");
             }
             // 赋分数据集合
@@ -136,14 +140,14 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
             DoubleSummaryStatistics totalStatistics = totalScoreList.stream().collect(Collectors.summarizingDouble(e -> e));
             double avgScore = totalStatistics.getAverage();
             long passCount = totalScoreList.stream().filter(e -> e >= passScore.doubleValue()).count();
-            BigDecimal passRate = BigDecimal.valueOf(passCount).divide(BigDecimal.valueOf(realityCount),4,BigDecimal.ROUND_HALF_DOWN);
+            BigDecimal passRate = BigDecimal.valueOf(passCount).divide(BigDecimal.valueOf(realityCount), 4, BigDecimal.ROUND_HALF_DOWN);
 
             // -------------------卷面分------------------------
             List<Double> paperTotalScoreList = totalDatasource.stream().filter(e -> !e.getAbsent()).map(e -> e.getTotalScore().doubleValue()).collect(Collectors.toList());
             DoubleSummaryStatistics paperTotalStatistics = paperTotalScoreList.stream().collect(Collectors.summarizingDouble(e -> e));
             double paperAvgScore = paperTotalStatistics.getAverage();
             long paperPassCount = paperTotalScoreList.stream().filter(e -> e >= passScore.doubleValue()).count();
-            BigDecimal paperPassRate = BigDecimal.valueOf(paperPassCount).divide(BigDecimal.valueOf(realityCount),4,BigDecimal.ROUND_HALF_DOWN);
+            BigDecimal paperPassRate = BigDecimal.valueOf(paperPassCount).divide(BigDecimal.valueOf(realityCount), 4, BigDecimal.ROUND_HALF_DOWN);
 
 
 
@@ -156,10 +160,10 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
             int pastTotalCount = pastDatasource.size();
             long pastRealityCount = pastDatasource.stream().filter(e -> !e.getAbsent()).count();
             long pastAbsentCount = pastDatasource.stream().filter(TAExamCourseRecord::getAbsent).count();
-            if (pastTotalCount != pastRealityCount + pastAbsentCount){
+            if (pastTotalCount != pastRealityCount + pastAbsentCount) {
                 throw ExceptionResultEnum.ERROR.exception("考试往届生人数数据异常");
             }
-            BigDecimal pastRealityRate = BigDecimal.valueOf(pastRealityCount).divide(BigDecimal.valueOf(realityCount),4,BigDecimal.ROUND_HALF_DOWN);
+            BigDecimal pastRealityRate = BigDecimal.valueOf(pastRealityCount).divide(BigDecimal.valueOf(realityCount), 4, BigDecimal.ROUND_HALF_DOWN);
 
             /*
                 该课程应届生成绩分析
@@ -171,16 +175,16 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
             int currentTotalCount = currentDatasource.size();
             long currentRealityCount = currentDatasource.stream().filter(e -> !e.getAbsent()).count();
             long currentAbsentCount = currentDatasource.stream().filter(TAExamCourseRecord::getAbsent).count();
-            if (currentTotalCount != currentRealityCount + currentAbsentCount){
+            if (currentTotalCount != currentRealityCount + currentAbsentCount) {
                 throw ExceptionResultEnum.ERROR.exception("考试应届生人数数据异常");
             }
-            BigDecimal currentRealityRate = BigDecimal.valueOf(currentRealityCount).divide(BigDecimal.valueOf(realityCount),4,BigDecimal.ROUND_HALF_DOWN);
+            BigDecimal currentRealityRate = BigDecimal.valueOf(currentRealityCount).divide(BigDecimal.valueOf(realityCount), 4, BigDecimal.ROUND_HALF_DOWN);
 
             // 通过率统计
             List<Double> currentScoreList = currentDatasource.stream().filter(e -> !e.getAbsent()).map(e -> e.getAssignedScore().doubleValue()).collect(Collectors.toList());
             DoubleSummaryStatistics currentStatistics = currentScoreList.stream().collect(Collectors.summarizingDouble(e -> e));
             long currentPassCount = currentScoreList.stream().filter(e -> e >= passScore.doubleValue()).count();
-            BigDecimal currentPassRate = BigDecimal.valueOf(currentPassCount).divide(BigDecimal.valueOf(currentRealityCount),4,BigDecimal.ROUND_HALF_DOWN);
+            BigDecimal currentPassRate = BigDecimal.valueOf(currentPassCount).divide(BigDecimal.valueOf(currentRealityCount), 4, BigDecimal.ROUND_HALF_DOWN);
 
             // 描述统计
             double currentMinScore = currentStatistics.getMin();
@@ -210,39 +214,39 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
             BigDecimal scoreRate;
             double standardAvgScore = currentDatasource.stream().collect(Collectors.summarizingDouble(e -> e.getTotalScore().doubleValue())).getAverage();
             if (standardAvgScore != 0 && totalScore.compareTo(BigDecimal.ZERO) > 0) {
-                scoreRate = BigDecimal.valueOf(standardAvgScore).divide(totalScore,4,BigDecimal.ROUND_HALF_DOWN);
+                scoreRate = BigDecimal.valueOf(standardAvgScore).divide(totalScore, 4, BigDecimal.ROUND_HALF_DOWN);
             } else {
                 scoreRate = BigDecimal.ZERO;
             }
             // 难度系数保留1位数
-            scoreRate = scoreRate.setScale(1,BigDecimal.ROUND_HALF_DOWN); // 难度系数保留1位有效数字
-            String difficulty = this.handleLevel(examId,effectiveCourseCode,"难度等级", scoreRate.doubleValue());
+            scoreRate = scoreRate.setScale(1, BigDecimal.ROUND_HALF_DOWN); // 难度系数保留1位有效数字
+            String difficulty = this.handleLevel(examId, effectiveCourseCode, "难度等级", scoreRate.doubleValue());
             //--------------------------应届-卷面成绩-----------------------
             List<Double> paperCurrentScoreList = currentDatasource.stream().filter(e -> !e.getAbsent()).map(e -> e.getTotalScore().doubleValue()).collect(Collectors.toList());
             DoubleSummaryStatistics paperCurrentStatistics = paperCurrentScoreList.stream().collect(Collectors.summarizingDouble(e -> e));
             double paperCurrentAvgScore = paperCurrentStatistics.getAverage();
             long paperCurrentPassCount = paperCurrentScoreList.stream().filter(e -> e >= passScore.doubleValue()).count();
-            BigDecimal paperCurrentPassRate = BigDecimal.valueOf(paperCurrentPassCount).divide(BigDecimal.valueOf(currentRealityCount),4,BigDecimal.ROUND_HALF_DOWN);
+            BigDecimal paperCurrentPassRate = BigDecimal.valueOf(paperCurrentPassCount).divide(BigDecimal.valueOf(currentRealityCount), 4, BigDecimal.ROUND_HALF_DOWN);
 
             /*
                 学院信息
              */
             // TODO: 2021/6/7 考察学院数量算进去往届和缺考的吗
             List<TBExamStudent> tbExamStudentList = tbExamStudentService.list(new QueryWrapper<TBExamStudent>().lambda()
-                    .eq(TBExamStudent::getExamId,examId).eq(TBExamStudent::getCourseCode,effectiveCourseCode));
+                    .eq(TBExamStudent::getExamId, examId).eq(TBExamStudent::getCourseCode, effectiveCourseCode));
 
             List<Long> teachCollegeIdList = tbExamStudentList.stream().map(TBExamStudent::getTeachCollegeId).distinct().collect(Collectors.toList());
             List<Long> inspectCollegeIdList = tbExamStudentList.stream().map(TBExamStudent::getInspectCollegeId).distinct().collect(Collectors.toList());
-            if (teachCollegeIdList.size() != 1){
+            if (teachCollegeIdList.size() != 1) {
                 throw ExceptionResultEnum.ERROR.exception("该课程有多个开课学院异常");
             }
             Long teachCollegeId = teachCollegeIdList.get(0);
             SysOrg tbSchoolCollege = sysOrgService.getById(teachCollegeId);
             String teachCollegeName;
-            if (Objects.isNull(tbSchoolCollege)){
+            if (Objects.isNull(tbSchoolCollege)) {
                 teachCollegeName = SystemConstant.DEFAULT_SIGN;
-            }else {
-                teachCollegeName= tbSchoolCollege.getName();
+            } else {
+                teachCollegeName = tbSchoolCollege.getName();
             }
             int inspectCollegeCount = inspectCollegeIdList.size();
 
@@ -295,25 +299,25 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
             taExamCourseList.add(taExamCourse);
         }
         taExamCourseService.saveBatch(taExamCourseList);
-        return " 't_a_exam_course' 表构建完毕 "  ;
+        return " 't_a_exam_course' 表构建完毕 ";
     }
 
     @Transactional(rollbackFor = Exception.class)
     @Override
-    public String buildAnalyzeExamCourseRecord(Long examId,String courseCode) {
+    public String buildAnalyzeExamCourseRecord(Long examId, String courseCode) {
         // 获取本次考试所有考试记录数据源
         List<TAExamCourseRecord> taExamCourseRecordDatasource = taExamCourseRecordService.list(new QueryWrapper<TAExamCourseRecord>().lambda()
-                .eq(TAExamCourseRecord::getExamId,examId)
-                .eq(TAExamCourseRecord::getAbsent,false)
-                .eq(TAExamCourseRecord::getStudentCurrent,true));
+                .eq(TAExamCourseRecord::getExamId, examId)
+                .eq(TAExamCourseRecord::getAbsent, false)
+                .eq(TAExamCourseRecord::getStudentCurrent, true));
 
-        List<String> effectiveCourseCodeList = tbExamCourseService.findEffectiveByExamId(examId,courseCode);
+        List<String> effectiveCourseCodeList = tbExamCourseService.findEffectiveByExamId(examId, courseCode);
 
         for (String effectiveCourseCode : effectiveCourseCodeList) {
             List<TAExamCourse> taExamCourseList = taExamCourseService.list(new QueryWrapper<TAExamCourse>().lambda()
-                    .eq(TAExamCourse::getExamId,examId)
-                    .eq(TAExamCourse::getCourseCode,effectiveCourseCode));
-            if (taExamCourseList.size() != 1){
+                    .eq(TAExamCourse::getExamId, examId)
+                    .eq(TAExamCourse::getCourseCode, effectiveCourseCode));
+            if (taExamCourseList.size() != 1) {
                 throw ExceptionResultEnum.ERROR.exception("考试课程分析数据获取失败");
             }
             TAExamCourse taExamCourse = taExamCourseList.get(0);
@@ -327,15 +331,15 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
                 long sameCount = dataSource.stream().filter(e -> e.getTotalScore().compareTo(totalScore) == 0).count(); // 和我相同的人数
                 int totalCount = dataSource.size(); //总人数
                 // 标准回归系数
-                BigDecimal standardizedCoefficients = (taExamCourseRecord.getAssignedScore().subtract(avgScore)).divide(standardDeviation,4,BigDecimal.ROUND_HALF_DOWN);
+                BigDecimal standardizedCoefficients = (taExamCourseRecord.getAssignedScore().subtract(avgScore)).divide(standardDeviation, 4, BigDecimal.ROUND_HALF_DOWN);
 
-                int percentGrade = this.handlePercentGrade(BigDecimal.valueOf(lowCount),BigDecimal.valueOf(sameCount),BigDecimal.valueOf(totalCount));
+                int percentGrade = this.handlePercentGrade(BigDecimal.valueOf(lowCount), BigDecimal.valueOf(sameCount), BigDecimal.valueOf(totalCount));
                 taExamCourseRecord.setPercentGrade(percentGrade);
 
-                String scoreLevel = this.handleLevel(examId,effectiveCourseCode,"百分等级",percentGrade);
+                String scoreLevel = this.handleLevel(examId, effectiveCourseCode, "百分等级", percentGrade);
                 taExamCourseRecord.setScoreLevel(scoreLevel);
                 taExamCourseRecord.setStandardizedCoefficients(standardizedCoefficients);
-                this.buildColData(taExamCourseRecord,dataSource); // 总成绩在学院的排名、排名等级档位、超过学院百分比
+                this.buildColData(taExamCourseRecord, dataSource); // 总成绩在学院的排名、排名等级档位、超过学院百分比
             }
             taExamCourseRecordService.saveOrUpdateBatch(dataSource);
         }
@@ -346,15 +350,15 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
     @Override
     public String buildAnalyzeExamCourseCollegeInspect(Long examId, String courseCode) {
         List<TAExamCourseRecord> recordDatasource = taExamCourseRecordService.list(new QueryWrapper<TAExamCourseRecord>().lambda()
-                .eq(TAExamCourseRecord::getExamId,examId));
+                .eq(TAExamCourseRecord::getExamId, examId));
         // 可分析有效课程信息
-        List<String> effectiveCourseCodeList = tbExamCourseService.findEffectiveByExamId(examId,courseCode);
+        List<String> effectiveCourseCodeList = tbExamCourseService.findEffectiveByExamId(examId, courseCode);
         List<TAExamCourseCollegeInspect> inspectCollegeList = new ArrayList<>();
 
         for (String effectiveCourseCode : effectiveCourseCodeList) {
             // 删除原有数据
             taExamCourseCollegeInspectService.remove(new QueryWrapper<TAExamCourseCollegeInspect>().lambda()
-                    .eq(TAExamCourseCollegeInspect::getExamId,examId).eq(TAExamCourseCollegeInspect::getCourseCode,effectiveCourseCode));
+                    .eq(TAExamCourseCollegeInspect::getExamId, examId).eq(TAExamCourseCollegeInspect::getCourseCode, effectiveCourseCode));
 
             // 本课程下所有应届考生考生记录
             List<TAExamCourseRecord> recordCourseCurrentDatasource = recordDatasource.stream()
@@ -384,7 +388,7 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
                 double lowerQuartile = MathUtil.calculateQuantile(assignedScoreList, QuantileEnum.LOWER_QUARTILE.getValue());
 
                 // TODO: 2021/6/7 缺考的学院信息处理
-                if (effectiveList.size() == 0){
+                if (effectiveList.size() == 0) {
                     minScore = 0;
                     maxScore = 0;
                     avgScore = 0;
@@ -435,16 +439,16 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
     @Override
     public String buildAnalyzeExamCourseClazz(Long examId, String courseCode) {
         List<TAExamCourseRecord> recordDatasource = taExamCourseRecordService.list(new QueryWrapper<TAExamCourseRecord>().lambda()
-                .eq(TAExamCourseRecord::getExamId,examId));
+                .eq(TAExamCourseRecord::getExamId, examId));
         // 可分析有效课程信息
-        List<String> effectiveCourseCodeList = tbExamCourseService.findEffectiveByExamId(examId,courseCode);
+        List<String> effectiveCourseCodeList = tbExamCourseService.findEffectiveByExamId(examId, courseCode);
 
         List<TAExamCourseClazz> taExamCourseClazzList = new ArrayList<>();
         for (String effectiveCourseCode : effectiveCourseCodeList) {
             // 删除原有数据
             taExamCourseClazzService.remove(new QueryWrapper<TAExamCourseClazz>().lambda()
-                    .eq(TAExamCourseClazz::getExamId,examId)
-                    .eq(TAExamCourseClazz::getCourseCode,effectiveCourseCode));
+                    .eq(TAExamCourseClazz::getExamId, examId)
+                    .eq(TAExamCourseClazz::getCourseCode, effectiveCourseCode));
 
             List<TAExamCourseRecord> recordCourseCurrentDatasource = recordDatasource.stream()
                     .filter(e -> effectiveCourseCode.equals(e.getCourseCode()) && e.getStudentCurrent()).collect(Collectors.toList());
@@ -469,20 +473,20 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
                 double avgScore = doubleSummaryStatistics.getAverage();
 
                 List<TBExamStudent> tbExamStudentList = tbExamStudentService.list(new QueryWrapper<TBExamStudent>().lambda()
-                        .eq(TBExamStudent::getExamId,examId)
-                        .eq(TBExamStudent::getCourseCode,effectiveCourseCode)
-                        .eq(TBExamStudent::getClazzId,clazzId));
+                        .eq(TBExamStudent::getExamId, examId)
+                        .eq(TBExamStudent::getCourseCode, effectiveCourseCode)
+                        .eq(TBExamStudent::getClazzId, clazzId));
                 List<Long> teachCollegeIdList = tbExamStudentList.stream().map(TBExamStudent::getTeachCollegeId).distinct().collect(Collectors.toList());
                 String collegeName = "";
                 for (Long collegeId : teachCollegeIdList) {
                     SysOrg tbSchoolCollege = sysOrgService.getById(collegeId);
-                    if (Objects.isNull(tbSchoolCollege)){
+                    if (Objects.isNull(tbSchoolCollege)) {
                         collegeName = collegeName + SystemConstant.DEFAULT_SIGN + ",";
                     } else {
                         collegeName = collegeName + tbSchoolCollege.getName() + ",";
                     }
                 }
-                collegeName = collegeName.substring(0,collegeName.length() - 1);
+                collegeName = collegeName.substring(0, collegeName.length() - 1);
 
                 TAExamCourseClazz taExamCourseClazz = new TAExamCourseClazz();
                 taExamCourseClazz.setId(SystemConstant.getDbUuid());
@@ -509,10 +513,10 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
     @Override
     public String AnalyzePointScoreRate(Long examId, String courseCode) throws Exception {
         // 可分析有效课程信息
-        List<String> effectiveCourseCodeList = tbExamCourseService.findEffectiveByExamId(examId,courseCode);
+        List<String> effectiveCourseCodeList = tbExamCourseService.findEffectiveByExamId(examId, courseCode);
 
         List<TAExamCourseRecord> dataSource = taExamCourseRecordService.list(new QueryWrapper<TAExamCourseRecord>().lambda()
-                .eq(TAExamCourseRecord::getExamId,examId));
+                .eq(TAExamCourseRecord::getExamId, examId));
 
         // 循环进入每次考试课程下
         for (String effectiveCourseCode : effectiveCourseCodeList) {
@@ -522,31 +526,31 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
 
             // 考察点数据源
             List<TBDimension> dimensionDatasource = tbDimensionService.list(new QueryWrapper<TBDimension>().lambda()
-                    .eq(TBDimension::getExamId,examId)
-                    .eq(TBDimension::getCourseCode,courseCode));
+                    .eq(TBDimension::getExamId, examId)
+                    .eq(TBDimension::getCourseCode, courseCode));
 
-            if (dimensionDatasource.size() < 1){
+            if (dimensionDatasource.size() < 1) {
                 continue;
             }
 
             // 删除原数据
             taExamCourseDioService.remove(new QueryWrapper<TAExamCourseDio>().lambda()
-                    .eq(TAExamCourseDio::getExamId,examId)
-                    .eq(TAExamCourseDio::getCourseCode,effectiveCourseCode));
+                    .eq(TAExamCourseDio::getExamId, examId)
+                    .eq(TAExamCourseDio::getCourseCode, effectiveCourseCode));
 
             taExamCourseRecordDioService.remove(new QueryWrapper<TAExamCourseRecordDio>().lambda()
-                    .eq(TAExamCourseRecordDio::getExamId,examId)
-                    .eq(TAExamCourseRecordDio::getCourseCode,effectiveCourseCode));
+                    .eq(TAExamCourseRecordDio::getExamId, examId)
+                    .eq(TAExamCourseRecordDio::getCourseCode, effectiveCourseCode));
 
             taExamCourseRecordModService.remove(new QueryWrapper<TAExamCourseRecordMod>().lambda()
-                    .eq(TAExamCourseRecordMod::getExamId,examId)
-                    .eq(TAExamCourseRecordMod::getCourseCode,courseCode));
+                    .eq(TAExamCourseRecordMod::getExamId, examId)
+                    .eq(TAExamCourseRecordMod::getCourseCode, courseCode));
 
             List<TBPaper> tbPaperList = tbPaperService.list(new QueryWrapper<TBPaper>().lambda()
-                    .eq(TBPaper::getExamId,examId)
-                    .eq(TBPaper::getCourseCode,courseCode));
+                    .eq(TBPaper::getExamId, examId)
+                    .eq(TBPaper::getCourseCode, courseCode));
 
-            if (tbPaperList.size() == 0){
+            if (tbPaperList.size() == 0) {
                 throw ExceptionResultEnum.ERROR.exception("试卷基础数据查找失败");
             }
             for (TBPaper tbPaper : tbPaperList) {
@@ -554,18 +558,18 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
                 Long paperId = tbPaper.getId();
                 // 试卷结构数据源
                 List<TBPaperStruct> tbPaperStructList = tbPaperStructService.list(new QueryWrapper<TBPaperStruct>().lambda()
-                        .eq(TBPaperStruct::getPaperId,paperId));
-                if (tbPaperStructList.size() == 0){
+                        .eq(TBPaperStruct::getPaperId, paperId));
+                if (tbPaperStructList.size() == 0) {
                     throw ExceptionResultEnum.ERROR.exception("试卷结构数据查找失败");
                 }
                 // 该试卷下所有考生作答数据
                 List<BasicAnswerDto> answerDtoList = tbAnswerService.findByPaperId(paperId);
-                if (answerDtoList.size() == 0){
+                if (answerDtoList.size() == 0) {
                     throw ExceptionResultEnum.ERROR.exception("试卷id为[" + paperId + "]的考生作答详细记录不存在");
                 }
 
                 // 5.计算每个考察点所对应的题目集合
-                Map<String, List<TBPaperStruct>> pointToPaper = this.handlePointToPaper(dimensionDatasource, tbPaperStructList, examId,courseCode);
+                Map<String, List<TBPaperStruct>> pointToPaper = this.handlePointToPaper(dimensionDatasource, tbPaperStructList, examId, courseCode);
 
                 // 计算每个模块对应的题目集合
                 Map<String, List<TBPaperStruct>> moduleToPaper = this.handleModuleToPaper(dimensionDatasource, tbPaperStructList, examId, courseCode);
@@ -586,7 +590,7 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
                     List<BasicAnswerDto> oneStudentAnswerDetailDataSource = answerDtoList.stream()
                             .filter(e -> taExamCourseRecord.getExamRecordId().equals(e.getExamRecordId()))
                             .collect(Collectors.toList());
-                    if (oneStudentAnswerDetailDataSource.size() == 0){
+                    if (oneStudentAnswerDetailDataSource.size() == 0) {
                         continue; // 当AB卷时,examPaperTikDataSource还是整体数据,所以会匹配不到,匹配不到的说明不是本套试卷,因此匹配不到的不能处理。
                     }
                     // 考察点得分率
@@ -624,6 +628,8 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
                         taExamCourseRecordDio.setExamRecordId(taExamCourseRecord.getExamRecordId());
                         taExamCourseRecordDio.setPaperId(taExamCourseRecord.getPaperId());
                         taExamCourseRecordDio.setExamId(taExamCourseRecord.getExamId());
+                        taExamCourseRecordDio.setStudentId(taExamCourseRecord.getStudentId());
+                        taExamCourseRecordDio.setStudentCode(taExamCourseRecord.getStudentCode());
                         taExamCourseRecordDio.setCourseCode(effectiveCourseCode);
                         taExamCourseRecordDio.setCourseName(basicCourseService.findByCourseCode(effectiveCourseCode).getName());
                         String[] dimCodeArr = s.split("-");
@@ -636,7 +642,7 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
                         taExamCourseRecordDio.setDimensionCode(dimensionCode);
                         taExamCourseRecordDio.setStudentScore(BigDecimal.valueOf(studentScore));
                         taExamCourseRecordDio.setScoreRate(BigDecimal.valueOf(rate));
-                        taExamCourseRecordDio.setProficiency(this.handleModuleProficiency(examId,effectiveCourseCode, dimensionType, rate));
+                        taExamCourseRecordDio.setProficiency(this.handleModuleProficiency(examId, effectiveCourseCode, dimensionType, rate));
                         taExamCourseRecordDio.setInspectCollegeId(inspectCollegeId);
                         taExamCourseRecordDio.setInspectCollegeName(inspectCollegeName);
                         taExamCourseRecordDioList.add(taExamCourseRecordDio);
@@ -681,9 +687,11 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
                         taExamCourseRecordMod.setTotalScore(BigDecimal.valueOf(studentScore));
                         taExamCourseRecordMod.setScoreRate(BigDecimal.valueOf(rate));
                         taExamCourseRecordMod.setFullScore(BigDecimal.valueOf(totalScore));
-                        taExamCourseRecordMod.setProficiency(this.handleModuleProficiency(examId,effectiveCourseCode,s,rate));
+                        taExamCourseRecordMod.setProficiency(this.handleModuleProficiency(examId, effectiveCourseCode, s, rate));
                         taExamCourseRecordMod.setInspectCollegeId(inspectCollegeId);
                         taExamCourseRecordMod.setInspectCollegeName(inspectCollegeName);
+                        taExamCourseRecordMod.setStudentId(taExamCourseRecord.getStudentId());
+                        taExamCourseRecordMod.setStudentCode(taExamCourseRecord.getStudentCode());
                         taExamCourseRecordModList.add(taExamCourseRecordMod);
                     }
                 }
@@ -732,11 +740,11 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
             }
 
             List<TAExamCourseRecordMod> examCourseRecordModList = taExamCourseRecordModService.list(new QueryWrapper<TAExamCourseRecordMod>().lambda()
-                    .eq(TAExamCourseRecordMod::getExamId,examId)
-                    .eq(TAExamCourseRecordMod::getCourseCode,effectiveCourseCode));
+                    .eq(TAExamCourseRecordMod::getExamId, examId)
+                    .eq(TAExamCourseRecordMod::getCourseCode, effectiveCourseCode));
 
             // 计算该考生在该模块得分率在该学院排名
-            List<TBModuleConfig> tbModuleConfigList = tbModuleConfigService.findDistinctModuleInfoByExamIdAndCourseCode(examId,effectiveCourseCode);
+            List<TBModuleConfig> tbModuleConfigList = tbModuleConfigService.findDistinctModuleInfoByExamIdAndCourseCode(examId, effectiveCourseCode);
             for (TAExamCourseRecordMod taExamCourseRecordMod : examCourseRecordModList) {
                 String moduleType = taExamCourseRecordMod.getModuleType();
                 Long myCollegeId = taExamCourseRecordMod.getInspectCollegeId();
@@ -747,7 +755,7 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
 
 
                 BigDecimal myScoreRate = taExamCourseRecordMod.getScoreRate();
-                double myNumber = sameColModuleList.stream().filter(e -> e.getScoreRate().compareTo(myScoreRate) > 0 ).count() + 1; //我在学院的排名
+                double myNumber = sameColModuleList.stream().filter(e -> e.getScoreRate().compareTo(myScoreRate) > 0).count() + 1; //我在学院的排名
                 taExamCourseRecordMod.setColRank((int) myNumber);
 
 
@@ -755,7 +763,7 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
                 double lowCount = sameColModuleList.stream().filter(e -> e.getScoreRate().compareTo(myScoreRate) < 0).count(); // 在学院该模块得分低于我的人数
                 double sameCount = sameColModuleList.stream().filter(e -> e.getScoreRate().compareTo(myScoreRate) == 0).count(); // 在学院该模块得分等于我的人数
                 double totalCount = sameColModuleList.size(); // 该学院总人数
-                int percentGrade = this.handlePercentGrade(BigDecimal.valueOf(lowCount),BigDecimal.valueOf(sameCount), BigDecimal.valueOf(totalCount)); // 该学生该模块成绩在该学院的百分等级
+                int percentGrade = this.handlePercentGrade(BigDecimal.valueOf(lowCount), BigDecimal.valueOf(sameCount), BigDecimal.valueOf(totalCount)); // 该学生该模块成绩在该学院的百分等级
                 taExamCourseRecordMod.setPercentGrade(percentGrade);
 
                 // 计算模块等级
@@ -774,7 +782,7 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
                         if (!formula.equals(LevelRuleEnum.COLLEGE_RANK.getValue())) {  // 当计算规则不为学院排名时,为了方便计算,将minNumber设置为1 使其无效
                             size = -1;
                         }
-                        taExamCourseRecordMod.setLevel(this.handleModuleRankLevel(examId,courseCode,moduleType, value, size));
+                        taExamCourseRecordMod.setLevel(this.handleModuleRankLevel(examId, courseCode, moduleType, value, size));
                     }
                 }
             }
@@ -788,14 +796,14 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
     @Override
     public String buildAnalyzeExamCourseCollegeInspectDio(Long examId, String courseCode) {
         // 可分析有效课程信息
-        List<String> effectiveCourseCodeList = tbExamCourseService.findEffectiveByExamId(examId,courseCode);
+        List<String> effectiveCourseCodeList = tbExamCourseService.findEffectiveByExamId(examId, courseCode);
         for (String effectiveCourseCode : effectiveCourseCodeList) {
             // 删除原有数据
             taExamCourseCollegeInspectDioService.remove(new QueryWrapper<TAExamCourseCollegeInspectDio>().lambda()
-                    .eq(TAExamCourseCollegeInspectDio::getExamId,examId)
-                    .eq(TAExamCourseCollegeInspectDio::getCourseCode,effectiveCourseCode));
+                    .eq(TAExamCourseCollegeInspectDio::getExamId, examId)
+                    .eq(TAExamCourseCollegeInspectDio::getCourseCode, effectiveCourseCode));
 
-            taExamCourseCollegeInspectDioService.insertByTAExamCourseRecordDio(examId,courseCode);
+            taExamCourseCollegeInspectDioService.insertByTAExamCourseRecordDio(examId, courseCode);
         }
         return "'t_a_exam_course_college_inspect_dio'表构建完成 ";
     }
@@ -804,26 +812,26 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
     @Override
     public String buildAnalyzePaperStruct(Long examId, String courseCode) {
         // 可分析有效课程信息
-        List<String> effectiveCourseCodeList = tbExamCourseService.findEffectiveByExamId(examId,courseCode);
+        List<String> effectiveCourseCodeList = tbExamCourseService.findEffectiveByExamId(examId, courseCode);
         for (String effectiveCourseCode : effectiveCourseCodeList) {
             List<TBPaper> tbPaperList = tbPaperService.list(new QueryWrapper<TBPaper>().lambda()
-                    .eq(TBPaper::getExamId,examId).eq(TBPaper::getCourseCode,effectiveCourseCode));
-            if (tbPaperList.size() == 0){
+                    .eq(TBPaper::getExamId, examId).eq(TBPaper::getCourseCode, effectiveCourseCode));
+            if (tbPaperList.size() == 0) {
                 throw ExceptionResultEnum.ERROR.exception("基础试卷信息异常");
             }
             // 删除原有数据
             taPaperStructService.remove(new QueryWrapper<TAPaperStruct>().lambda()
-                    .eq(TAPaperStruct::getExamId,examId)
-                    .eq(TAPaperStruct::getCourseCode,effectiveCourseCode));
+                    .eq(TAPaperStruct::getExamId, examId)
+                    .eq(TAPaperStruct::getCourseCode, effectiveCourseCode));
             List<TAPaperStruct> taPaperStructList = new ArrayList<>();
             // 该课程有效试卷结构数据
-            List<ValidAnswerDetailDto> answerDetailDtoList = tbAnswerService.findValid(examId,courseCode);
+            List<ValidAnswerDetailDto> answerDetailDtoList = tbAnswerService.findValid(examId, courseCode);
             for (TBPaper tbPaper : tbPaperList) {
                 Long paperId = tbPaper.getId();
                 String paperType = tbPaper.getPaperType();
                 List<TBPaperStruct> tbPaperStructList = tbPaperStructService.list(new QueryWrapper<TBPaperStruct>().lambda()
-                        .eq(TBPaperStruct::getPaperId,paperId));
-                if (tbPaperStructList.size() == 0){
+                        .eq(TBPaperStruct::getPaperId, paperId));
+                if (tbPaperStructList.size() == 0) {
                     throw ExceptionResultEnum.ERROR.exception("试卷结构数据异常");
                 }
                 for (TBPaperStruct paperStruct : tbPaperStructList) {
@@ -841,9 +849,9 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
                             .collect(Collectors.summarizingDouble(e -> e.getScore().doubleValue()));
                     BigDecimal fullScore = paperStruct.getFullScore();
                     double scoreAvg = descriptiveStatistics.getAverage();
-                    BigDecimal scoreRate = BigDecimal.valueOf(scoreAvg).divide(fullScore,4,BigDecimal.ROUND_HALF_DOWN);
-                    scoreRate = scoreRate.setScale(1,BigDecimal.ROUND_HALF_DOWN);
-                    String difficult = this.analyzeDifficult(examId,courseCode, scoreRate.doubleValue());
+                    BigDecimal scoreRate = BigDecimal.valueOf(scoreAvg).divide(fullScore, 4, BigDecimal.ROUND_HALF_DOWN);
+                    scoreRate = scoreRate.setScale(1, BigDecimal.ROUND_HALF_DOWN);
+                    String difficult = this.analyzeDifficult(examId, courseCode, scoreRate.doubleValue());
 
                     double validity = this.calculateValidity(oneQuestionAnswerDetailList, fullScore.doubleValue());
 
@@ -854,6 +862,19 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
                     taPaperStruct.setSchoolId(tbExamService.getById(examId).getSchoolId());
                     taPaperStruct.setCourseCode(courseCode);
                     taPaperStruct.setCourseName(basicCourseService.findByCourseCode(courseCode).getName());
+                    taPaperStruct.setPaperId(paperId);
+                    taPaperStruct.setQuestionName(paperStruct.getQuestionName());
+                    taPaperStruct.setNumberType(paperStruct.getNumberType());
+                    taPaperStruct.setBigQuestionNumber(paperStruct.getBigQuestionNumber());
+                    taPaperStruct.setSmallQuestionNumber(paperStruct.getSmallQuestionNumber());
+                    taPaperStruct.setQuestionType(paperStruct.getQuestionType());
+                    taPaperStruct.setFullScore(paperStruct.getFullScore());
+                    taPaperStruct.setScoreRules(paperStruct.getScoreRules());
+                    taPaperStruct.setRulesDesc(paperStruct.getRulesDesc());
+                    taPaperStruct.setKnowledgeDimension(paperStruct.getKnowledgeDimension());
+                    taPaperStruct.setAbilityDimension(paperStruct.getAbilityDimension());
+                    taPaperStruct.setLiteracyDimension(paperStruct.getLiteracyDimension());
+
                     taPaperStruct.setScoreRate(scoreRate);
                     taPaperStruct.setDifficult(difficult);
                     taPaperStruct.setValidity(BigDecimal.valueOf(validity));
@@ -866,16 +887,101 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
         return " 't_a_paper_struct'表构建成功 ";
     }
 
+    @Transactional(rollbackFor = Exception.class)
+    @Override
+    public String buildExamPaperDifficult(Long examId, String courseCode) {
+        // 可分析有效课程信息
+        List<String> effectiveCourseCodeList = tbExamCourseService.findEffectiveByExamId(examId, courseCode);
+
+        for (String effectiveCourseCode : effectiveCourseCodeList) {
+            taExamCourseDifficultService.remove(new QueryWrapper<TAExamCourseDifficult>().lambda()
+                    .eq(TAExamCourseDifficult::getExamId, examId)
+                    .eq(TAExamCourseDifficult::getCourseCode, courseCode));
+
+            List<TAExamCourseDifficult> taExamCourseDifficultList = new ArrayList<>();
+
+            List<TBCommonLevelConfig> configLevelDatasource = tbCommonLevelConfigService.list(new QueryWrapper<TBCommonLevelConfig>().lambda()
+                    .eq(TBCommonLevelConfig::getExamId, examId).eq(TBCommonLevelConfig::getCourseCode, effectiveCourseCode));// 该科目试题难度情况数据源
+
+            List<TAPaperStruct> questionDatasource = taPaperStructService.list(new QueryWrapper<TAPaperStruct>().lambda()
+                    .eq(TAPaperStruct::getExamId, examId).eq(TAPaperStruct::getCourseCode, effectiveCourseCode));// 该科目试题情况数据源
+
+            LinkedList<AnswerDetailBean> answerDetailDatasource = tbAnswerService.findValidAnswerDetailWithPap(examId, courseCode);
+            Set<Long> paperTypeList = questionDatasource.stream().map(TAPaperStruct::getPaperId).collect(Collectors.toSet());
+
+            for (Long paperId : paperTypeList) {
+                for (TBCommonLevelConfig levelTemp : configLevelDatasource) {
+                    String interpret = levelTemp.getInterpret();
+                    String scope = levelTemp.getScope();
+
+                    List<TAPaperStruct> questionList = questionDatasource.stream()
+                            .filter(e -> paperId.equals(e.getPaperId()) && interpret.equals(e.getDifficult()))
+                            .collect(Collectors.toList()); // 题目信息
+
+                    List<AnswerDetailBean> answerDetailForSch = answerDetailDatasource.stream()
+                            .filter(e -> paperId.equals(e.getPaperId()) && interpret.equals(e.getDifficult()))
+                            .collect(Collectors.toList());
+
+                    double schAvgScoreRate = answerDetailForSch.stream()
+                            .collect(Collectors.summarizingDouble(AnswerDetailBean::getScoreRate))
+                            .getAverage();
+
+                    // 学院id集合
+                    List<Long> collegeIdList = taExamCourseRecordService.list(new QueryWrapper<TAExamCourseRecord>().lambda()
+                            .eq(TAExamCourseRecord::getExamId, examId)
+                            .eq(TAExamCourseRecord::getCourseCode, courseCode)
+                            .eq(TAExamCourseRecord::getPaperId, paperId)
+                            .eq(TAExamCourseRecord::getAbsent, false)
+                            .eq(TAExamCourseRecord::getStudentCurrent, true))
+                            .stream()
+                            .map(TAExamCourseRecord::getInspectCollegeId).distinct()
+                            .collect(Collectors.toList());
+
+                    for (Long collegeId : collegeIdList) {
+                        List<AnswerDetailBean> answerDetailForCol = answerDetailForSch.stream()
+                                .filter(e -> collegeId.equals(e.getCollegeId())).collect(Collectors.toList());
+
+                        double colAvgScoreRate = answerDetailForCol.stream()
+                                .collect(Collectors.summarizingDouble(AnswerDetailBean::getScoreRate))
+                                .getAverage();
+
+                        // 得分率保留2位小数处理
+                        Integer count = questionList.size();
+
+                        TAExamCourseDifficult taExamCourseDifficult = new TAExamCourseDifficult();
+                        taExamCourseDifficult.setId(SystemConstant.getDbUuid());
+                        taExamCourseDifficult.setExamId(examId);
+                        taExamCourseDifficult.setCourseCode(effectiveCourseCode);
+                        taExamCourseDifficult.setCourseName(basicCourseService.findByCourseCode(effectiveCourseCode).getName());
+                        taExamCourseDifficult.setCollegeId(collegeId);
+                        taExamCourseDifficult.setSchoolId(tbExamService.getById(examId).getSchoolId());
+                        taExamCourseDifficult.setInterpret(interpret);
+                        taExamCourseDifficult.setCount(count);
+                        taExamCourseDifficult.setScope(scope);
+                        taExamCourseDifficult.setSchAvgScoreRate(BigDecimal.valueOf(schAvgScoreRate));
+                        taExamCourseDifficult.setColAvgScoreRate(BigDecimal.valueOf(colAvgScoreRate));
+
+                        taExamCourseDifficultList.add(taExamCourseDifficult);
+                    }
+                }
+            }
+
+            taExamCourseDifficultService.saveBatch(taExamCourseDifficultList);
+        }
+
+        return "'t_a_exam_course_difficult' 表构建完成";
+    }
+
     @Transactional(rollbackFor = Exception.class)
     @Override
     public String buildAnalyzeExamTotal(Long examId) {
         // 删除原数据
         taExamTotalService.remove(new QueryWrapper<TAExamTotal>().lambda()
-                .eq(TAExamTotal::getExamId,examId));
+                .eq(TAExamTotal::getExamId, examId));
 
         // 数据源
         List<TAExamCourseRecord> taExamCourseRecordList = taExamCourseRecordService.list(new QueryWrapper<TAExamCourseRecord>().lambda()
-                .eq(TAExamCourseRecord::getExamId,examId));
+                .eq(TAExamCourseRecord::getExamId, examId));
 
         //考察学院
         // TODO: 2021/6/8 是否计算只有缺考的学院 是否计算只有往届的学院
@@ -884,13 +990,13 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
         // 考察学院数量
         int collegeCount = inspectCollegeInfo.size();
         String inspectCollegeNames = "";
-        if (collegeCount > 0){
+        if (collegeCount > 0) {
             for (Long inspectCollegeId : inspectCollegeInfo) {
                 SysOrg college = sysOrgService.getById(inspectCollegeId);
                 inspectCollegeNames = inspectCollegeNames + college.getName() + "、";
             }
             // 考察学院名称
-            inspectCollegeNames = inspectCollegeNames.substring(0,inspectCollegeNames.length() - 1);
+            inspectCollegeNames = inspectCollegeNames.substring(0, inspectCollegeNames.length() - 1);
         }
 
         // 课程
@@ -944,18 +1050,18 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
     @Override
     public String buildAnalyzeExamCourseCollegeTeacher(Long examId, String courseCode) {
         // 可分析有效课程信息
-        List<String> effectiveCourseCodeList = tbExamCourseService.findEffectiveByExamId(examId,courseCode);
+        List<String> effectiveCourseCodeList = tbExamCourseService.findEffectiveByExamId(examId, courseCode);
         for (String effectiveCourseCode : effectiveCourseCodeList) {
             // 删除该课程原有分析
             taExamCourseCollegeTeacherService.remove(new QueryWrapper<TAExamCourseCollegeTeacher>().lambda()
-                    .eq(TAExamCourseCollegeTeacher::getExamId,examId)
-                    .eq(TAExamCourseCollegeTeacher::getCourseCode,courseCode));
+                    .eq(TAExamCourseCollegeTeacher::getExamId, examId)
+                    .eq(TAExamCourseCollegeTeacher::getCourseCode, courseCode));
 
             List<TAExamCourseCollegeTeacher> taExamCourseCollegeTeacherList = new ArrayList<>();
             // 整体该课程下数据源
             List<TAExamCourseRecord> dataSource = taExamCourseRecordService.list(new QueryWrapper<TAExamCourseRecord>().lambda()
-                    .eq(TAExamCourseRecord::getExamId,examId)
-                    .eq(TAExamCourseRecord::getCourseCode,courseCode));
+                    .eq(TAExamCourseRecord::getExamId, examId)
+                    .eq(TAExamCourseRecord::getCourseCode, courseCode));
 
             // 考察学院
             Set<Long> inspectCollegeIdSet = dataSource.stream().map(TAExamCourseRecord::getInspectCollegeId).collect(Collectors.toSet());
@@ -982,7 +1088,7 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
                     int totalCount = teacherRecordList.size();
                     List<TAExamCourseRecord> teacherEffectiveList = teacherRecordList.stream().filter(e -> !e.getAbsent()).collect(Collectors.toList());
                     int realityCount = teacherEffectiveList.size();
-                    if (realityCount == 0){
+                    if (realityCount == 0) {
                         continue;
                     }
                     int absentCount = totalCount - realityCount;
@@ -1021,12 +1127,12 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
 
                     // 开课学院数据
                     List<Long> teachCollegeIdList = teacherEffectiveList.stream().map(TAExamCourseRecord::getTeachCollegeId).distinct().collect(Collectors.toList());
-                    if (teachCollegeIdList.size() > 1){
+                    if (teachCollegeIdList.size() > 1) {
                         throw ExceptionResultEnum.ERROR.exception("有多个开课学院");
                     }
                     Long teachCollegeId = teachCollegeIdList.get(0);
                     String teachCollegeName = SystemConstant.DEFAULT_SIGN;
-                    if (teachCollegeId > 0){
+                    if (teachCollegeId > 0) {
                         teachCollegeName = sysOrgService.getById(teachCollegeId).getName();
                     }
 
@@ -1076,15 +1182,15 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
     @Override
     public String buildAnalyzeExamCourseTeacher(Long examId, String courseCode) {
         // 可分析有效课程信息
-        List<String> effectiveCourseCodeList = tbExamCourseService.findEffectiveByExamId(examId,courseCode);
+        List<String> effectiveCourseCodeList = tbExamCourseService.findEffectiveByExamId(examId, courseCode);
         for (String effectiveCourseCode : effectiveCourseCodeList) {
             taExamCourseTeacherService.remove(new QueryWrapper<TAExamCourseTeacher>().lambda()
-                    .eq(TAExamCourseTeacher::getExamId,examId)
-                    .eq(TAExamCourseTeacher::getCourseCode,courseCode));
+                    .eq(TAExamCourseTeacher::getExamId, examId)
+                    .eq(TAExamCourseTeacher::getCourseCode, courseCode));
 
             List<TAExamCourseTeacher> taExamCourseTeacherList = new ArrayList<>();
             List<TAExamCourseRecord> dataSource = taExamCourseRecordService.list(new QueryWrapper<TAExamCourseRecord>().lambda()
-                    .eq(TAExamCourseRecord::getExamId,examId).eq(TAExamCourseRecord::getCourseCode,effectiveCourseCode));
+                    .eq(TAExamCourseRecord::getExamId, examId).eq(TAExamCourseRecord::getCourseCode, effectiveCourseCode));
             List<TAExamCourseRecord> currentSource = dataSource.stream().filter(TAExamCourseRecord::getStudentCurrent).collect(Collectors.toList());
 
             Set<Long> teacherIdList = currentSource.stream().map(TAExamCourseRecord::getTeacherId).collect(Collectors.toSet());
@@ -1093,7 +1199,7 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
                         .filter(e -> teacherId.equals(e.getTeacherId())).collect(Collectors.toList());
                 int totalCount = teacherRecordList.size();
                 List<TAExamCourseRecord> effectiveList = teacherRecordList.stream().filter(e -> !e.getAbsent()).collect(Collectors.toList());
-                if (effectiveList.size() == 0){
+                if (effectiveList.size() == 0) {
                     continue;
                 }
                 int realityCount = effectiveList.size();
@@ -1157,6 +1263,23 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
         return " 't_a_exam_course_teacher'表构建完毕 ";
     }
 
+    @Transactional(rollbackFor = Exception.class)
+    @Override
+    public String finishCalculate(Long examId, String courseCode) {
+        // 可分析有效课程信息
+        List<String> effectiveCourseCodeList = tbExamCourseService.findEffectiveByExamId(examId, courseCode);
+        List<TBExamCourse> tbExamCourseList = new ArrayList<>();
+        for (String effectiveCourseCode : effectiveCourseCodeList) {
+            TBExamCourse tbExamCourse = tbExamCourseService.getOne(new QueryWrapper<TBExamCourse>().lambda()
+                    .eq(TBExamCourse::getExamId, examId)
+                    .eq(TBExamCourse::getCourseCode, effectiveCourseCode));
+            tbExamCourse.setPublishStatus(PublishStatusEnum.UN_PUBLISH);
+            tbExamCourseList.add(tbExamCourse);
+        }
+        tbExamCourseService.updateBatchById(tbExamCourseList);
+        return " 't_b_exam_course' 表状态更新完成";
+    }
+
     /**
      * 计算百分位等级
      *
@@ -1168,8 +1291,8 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
     private int handlePercentGrade(BigDecimal lowCount, BigDecimal sameCount, BigDecimal totalCount) {
         // ((lowCount + sameCount * 0.5) / totalCount) * 100
         BigDecimal percentGrade = (lowCount.add(sameCount.multiply(new BigDecimal("0.5"))))
-                .divide(totalCount,4,BigDecimal.ROUND_HALF_DOWN).multiply(new BigDecimal("100"));
-        int result = percentGrade.setScale(0,BigDecimal.ROUND_HALF_DOWN).intValue();
+                .divide(totalCount, 4, BigDecimal.ROUND_HALF_DOWN).multiply(new BigDecimal("100"));
+        int result = percentGrade.setScale(0, BigDecimal.ROUND_HALF_DOWN).intValue();
         if (result == 100) {
             result = 99;
         }
@@ -1186,11 +1309,11 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
      * @param value 值
      * @return 档位
      */
-    private String handleLevel(Long examId,String courseCode, String type, double value) {
+    private String handleLevel(Long examId, String courseCode, String type, double value) {
         List<TBCommonLevelConfig> levelList = tbCommonLevelConfigService.list(new QueryWrapper<TBCommonLevelConfig>().lambda()
-                .eq(TBCommonLevelConfig::getExamId,examId)
-                .eq(TBCommonLevelConfig::getCourseCode,courseCode)
-                .eq(TBCommonLevelConfig::getLevelType,type));
+                .eq(TBCommonLevelConfig::getExamId, examId)
+                .eq(TBCommonLevelConfig::getCourseCode, courseCode)
+                .eq(TBCommonLevelConfig::getLevelType, type));
         String level = "";
         if ("百分等级".equals(type) || "难度等级".equals(type)) {
             for (TBCommonLevelConfig levelTemp : levelList) {
@@ -1224,7 +1347,8 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
 
     /**
      * 构建和学院比较的有关信息(超过学院百分比、排名、排名等级)
-     * @param taExamCourseRecord 该学生数据
+     *
+     * @param taExamCourseRecord     该学生数据
      * @param taExamCourseRecordList 该课程下学生数据
      */
     private void buildColData(TAExamCourseRecord taExamCourseRecord, List<TAExamCourseRecord> taExamCourseRecordList) {
@@ -1237,7 +1361,7 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
         double lowCount = examRecordSameCol.stream().filter(e -> e.getAssignedScore().compareTo(taExamCourseRecord.getAssignedScore()) < 0).count();
         BigDecimal overCollegeRate;
         if (examRecordSameCol.size() > 1) {
-            overCollegeRate = BigDecimal.valueOf(lowCount).divide(BigDecimal.valueOf(examRecordSameCol.size() - 1),4,BigDecimal.ROUND_HALF_DOWN);
+            overCollegeRate = BigDecimal.valueOf(lowCount).divide(BigDecimal.valueOf(examRecordSameCol.size() - 1), 4, BigDecimal.ROUND_HALF_DOWN);
         } else {
             overCollegeRate = BigDecimal.ONE;
         }
@@ -1251,9 +1375,8 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
         //计算在学院排名的档次
         double size = examRecordSameCol.size();
         List<TBCommonRankLevelConfig> tbCommonRankLevelConfigList = tbCommonRankLevelConfigService.list(new QueryWrapper<TBCommonRankLevelConfig>().lambda()
-                .eq(TBCommonRankLevelConfig::getExamId,taExamCourseRecord.getExamId())
-                .eq(TBCommonRankLevelConfig::getCourseCode,taExamCourseRecord.getCourseCode()));
-
+                .eq(TBCommonRankLevelConfig::getExamId, taExamCourseRecord.getExamId())
+                .eq(TBCommonRankLevelConfig::getCourseCode, taExamCourseRecord.getCourseCode()));
 
 
         if (tbCommonRankLevelConfigList.size() < 1) {
@@ -1297,8 +1420,8 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
      *
      * @param dimensionDatasource 知识点数据源
      * @param tbPaperStructList   试卷结构数据源
-     * @param examId  考试id
-     * @param courseCode  课程编号
+     * @param examId              考试id
+     * @param courseCode          课程编号
      * @return 键值对 (类型-考察点 -> 考察此考察点的题目信息集合) 例如 :”知识模块-A“,List<>
      */
     private Map<String, List<TBPaperStruct>> handlePointToPaper(List<TBDimension> dimensionDatasource, List<TBPaperStruct> tbPaperStructList, Long examId, String courseCode) throws NoSuchFieldException, NoSuchMethodException, InvocationTargetException, IllegalAccessException {
@@ -1306,7 +1429,7 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
 
         // 模块配置信息
         List<TBModuleConfig> tbModuleConfigList = tbModuleConfigService.findDistinctModuleInfoByExamIdAndCourseCode(examId, courseCode);
-        if (tbModuleConfigList.size() < 1){
+        if (tbModuleConfigList.size() < 1) {
             throw ExceptionResultEnum.ERROR.exception("基础模块信息异常");
         }
 
@@ -1363,8 +1486,8 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
      *
      * @param dimensionDatasource 知识点数据源
      * @param tbPaperStructList   试卷结构数据源
-     * @param examId  考试id
-     * @param courseCode  课程编号
+     * @param examId              考试id
+     * @param courseCode          课程编号
      * @return 键值对 (考察模块 -> 考察此考模块的题目信息集合) 例如 :”知识模块“,List<>
      * @throws Exception 反射异常
      */
@@ -1373,7 +1496,7 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
 
         // 模块配置信息
         List<TBModuleConfig> tbModuleConfigList = tbModuleConfigService.findDistinctModuleInfoByExamIdAndCourseCode(examId, courseCode);
-        if (tbModuleConfigList.size() < 1){
+        if (tbModuleConfigList.size() < 1) {
             throw ExceptionResultEnum.ERROR.exception("基础模块信息异常");
         }
 
@@ -1420,17 +1543,17 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
     /**
      * 根据考察点得分率计算该考察点的熟练度
      *
-     * @param examId  考试id
-     * @param courseCode  课程编号
+     * @param examId        考试id
+     * @param courseCode    课程编号
      * @param dimensionType 考察点类型
-     * @param value   得分率
+     * @param value         得分率
      * @return 熟练度等级
      */
     private String handleModuleProficiency(Long examId, String courseCode, String dimensionType, double value) {
         List<TBModuleProficiency> tbModuleProficiencyList = tbModuleProficiencyService.list(new QueryWrapper<TBModuleProficiency>().lambda()
-                .eq(TBModuleProficiency::getExamId,examId)
-                .eq(TBModuleProficiency::getCourseCode,courseCode)
-                .eq(TBModuleProficiency::getModuleType,dimensionType));
+                .eq(TBModuleProficiency::getExamId, examId)
+                .eq(TBModuleProficiency::getCourseCode, courseCode)
+                .eq(TBModuleProficiency::getModuleType, dimensionType));
 
         if (tbModuleProficiencyList.size() < 1) {
             throw ExceptionResultEnum.ERROR.exception("模块二级维度熟练度配置信息不存在");
@@ -1465,18 +1588,18 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
     /**
      * 处理学生在该模块成绩在该学院的排名等级
      *
-     * @param examId  考试id
-     * @param courseCode  考试编号
-     * @param module 模块类型
-     * @param value  值(排名、得分率、百分等级)
-     * @param size   该学院最低分排名(当其不为排名时,赋值-1)
+     * @param examId     考试id
+     * @param courseCode 考试编号
+     * @param module     模块类型
+     * @param value      值(排名、得分率、百分等级)
+     * @param size       该学院最低分排名(当其不为排名时,赋值-1)
      * @return 排名等级编号
      */
     private String handleModuleRankLevel(Long examId, String courseCode, String module, double value, double size) {
         List<TBModuleConfig> tbModuleConfigList = tbModuleConfigService.list(new QueryWrapper<TBModuleConfig>().lambda()
-                .eq(TBModuleConfig::getExamId,examId)
-                .eq(TBModuleConfig::getCourseCode,courseCode)
-                .eq(TBModuleConfig::getModuleType,module));
+                .eq(TBModuleConfig::getExamId, examId)
+                .eq(TBModuleConfig::getCourseCode, courseCode)
+                .eq(TBModuleConfig::getModuleType, module));
 
         String result = null;
         if (size < tbModuleConfigList.size() && size > 0) {
@@ -1518,16 +1641,16 @@ public class AnalyzeForStudentServiceImpl implements AnalyzeForStudentService {
     /**
      * 根据得分率计算每道题目的难度
      *
-     * @param examId  考试id
+     * @param examId     考试id
      * @param courseCode 课程编号
-     * @param scoreRate 题目得分率
+     * @param scoreRate  题目得分率
      * @return 难度
      */
     private String analyzeDifficult(Long examId, String courseCode, double scoreRate) {
         List<TBCommonLevelConfig> levelConfigList = tbCommonLevelConfigService.list(new QueryWrapper<TBCommonLevelConfig>().lambda()
-                .eq(TBCommonLevelConfig::getExamId,examId)
-                .eq(TBCommonLevelConfig::getCourseCode,courseCode)
-                .eq(TBCommonLevelConfig::getLevelType,"难度等级"));
+                .eq(TBCommonLevelConfig::getExamId, examId)
+                .eq(TBCommonLevelConfig::getCourseCode, courseCode)
+                .eq(TBCommonLevelConfig::getLevelType, "难度等级"));
         String difficult = "";
         for (TBCommonLevelConfig levelConfig : levelConfigList) {
             Map<String, Object> scopeMap = AnalyzeScopeUtil.analyzeScope(levelConfig.getScope());

+ 291 - 12
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/service/impl/ReportCommonServiceImpl.java

@@ -3,21 +3,21 @@ package com.qmth.teachcloud.report.business.service.impl;
 import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
 import com.google.gson.Gson;
 import com.qmth.teachcloud.common.enums.ExceptionResultEnum;
-import com.qmth.teachcloud.report.business.bean.result.CourseInfoResult;
-import com.qmth.teachcloud.report.business.bean.result.DescriptiveStatisticsResult;
-import com.qmth.teachcloud.report.business.bean.result.TAExamCourseCollegeInspectResult;
-import com.qmth.teachcloud.report.business.bean.result.TBPaperInfoResult;
+import com.qmth.teachcloud.report.business.bean.result.*;
+import com.qmth.teachcloud.report.business.entity.TBCommonLevelConfig;
+import com.qmth.teachcloud.report.business.entity.TBDimension;
 import com.qmth.teachcloud.report.business.entity.TBPaper;
-import com.qmth.teachcloud.report.business.service.ReportCommonService;
-import com.qmth.teachcloud.report.business.service.TAExamCourseCollegeInspectService;
-import com.qmth.teachcloud.report.business.service.TBPaperService;
+import com.qmth.teachcloud.report.business.enums.GradeScopeEnum;
+import com.qmth.teachcloud.report.business.enums.PiecewiseScopeEnum;
+import com.qmth.teachcloud.report.business.service.*;
+import com.qmth.teachcloud.report.business.utils.AnalyzeScopeUtil;
+import com.qmth.teachcloud.report.business.utils.MathUtil;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 import org.springframework.stereotype.Service;
 
 import javax.annotation.Resource;
-import java.util.List;
-import java.util.Set;
+import java.util.*;
 import java.util.stream.Collectors;
 
 /**
@@ -37,6 +37,24 @@ public class ReportCommonServiceImpl implements ReportCommonService {
     @Resource
     TAExamCourseCollegeInspectService taExamCourseCollegeInspectService;
 
+    @Resource
+    TAExamCourseRecordService taExamCourseRecordService;
+
+    @Resource
+    TBDimensionService tbDimensionService;
+
+    @Resource
+    TBCommonLevelConfigService tbCommonLevelConfigService;
+
+    @Resource
+    TBPaperStructService tbPaperStructService;
+
+    @Resource
+    TBAnswerService tbAnswerService;
+
+    @Resource
+    TAExamCourseCollegeTeacherService taExamCourseCollegeTeacherService;
+
     /**
      * 学院学科报表查询科目信息
      *
@@ -71,7 +89,7 @@ public class ReportCommonServiceImpl implements ReportCommonService {
 
         // 学院该科目的描述统计
         List<TAExamCourseCollegeInspectResult> collegeDescriptiveStatisticsList = taExamCourseCollegeInspectResultList
-                .stream().filter(e -> collegeId.intValue() == e.getCollegeId().intValue()).collect(Collectors.toList());
+                .stream().filter(e -> collegeId.longValue() == e.getCollegeId().longValue()).collect(Collectors.toList());
         if (collegeDescriptiveStatisticsList.size() != 1) {
             throw ExceptionResultEnum.DATA_COUNT_EXCEPTION.exception();
         }
@@ -95,7 +113,268 @@ public class ReportCommonServiceImpl implements ReportCommonService {
      * @return
      */
     @Override
-    public Object findCourseDistribution(Long examId, String courseCode, Long collegeId) {
-        return null;
+    public CollegeAndSchoolGradeDistributionResult findCourseDistribution(Long examId, String courseCode, Long collegeId) {
+        List<ExamRecordResult> examPaperTikForSchool = taExamCourseRecordService.findExamRecordByExamIdAndCourseCode(examId, courseCode);
+        List<ExamRecordResult> examPaperTikForCollege = examPaperTikForSchool
+                .stream().filter(e -> collegeId.longValue() == e.getCollegeId().longValue()).collect(Collectors.toList());
+
+        double colTotalCount = examPaperTikForCollege.size(); // 学院总参考人数
+        double schTotalCount = examPaperTikForSchool.size(); // 全校总参考人数
+        if (schTotalCount < 1 || colTotalCount < 1) {
+            throw ExceptionResultEnum.DATA_ERROR.exception();
+        }
+
+        // 计算成绩分布图
+        List<GradeDistributionResult> gradeDistributionList = new ArrayList<>();
+        for (GradeScopeEnum value : GradeScopeEnum.values()) {
+            String describe = value.getDescribe();
+            double colCount = 0;
+            double schCount = 0;
+
+            Map<String, Object> scopeMap = AnalyzeScopeUtil.analyzeScope(value.getScope());
+            String minSign = String.valueOf(scopeMap.get("minSign"));
+            String maxSign = String.valueOf(scopeMap.get("maxSign"));
+            double minValue = Double.parseDouble(String.valueOf(scopeMap.get("minValue")));
+            double maxValue = Double.parseDouble(String.valueOf(scopeMap.get("maxValue")));
+            if ("(".equals(minSign) && ")".equals(maxSign)) {
+                colCount = (int) examPaperTikForCollege.stream()
+                        .filter(e -> minValue < e.getAssignedScore().doubleValue() && maxValue > e.getAssignedScore().doubleValue()).count();
+                schCount = (int) examPaperTikForSchool.stream()
+                        .filter(e -> minValue < e.getAssignedScore().doubleValue() && maxValue > e.getAssignedScore().doubleValue()).count();
+
+            } else if ("(".equals(minSign) && "]".equals(maxSign)) {
+                colCount = (int) examPaperTikForCollege.stream()
+                        .filter(e -> minValue < e.getAssignedScore().doubleValue() && maxValue >= e.getAssignedScore().doubleValue()).count();
+                schCount = (int) examPaperTikForSchool.stream()
+                        .filter(e -> minValue < e.getAssignedScore().doubleValue() && maxValue >= e.getAssignedScore().doubleValue()).count();
+
+            } else if ("[".equals(minSign) && ")".equals(maxSign)) {
+                colCount = (int) examPaperTikForCollege.stream()
+                        .filter(e -> minValue <= e.getAssignedScore().doubleValue() && maxValue > e.getAssignedScore().doubleValue()).count();
+                schCount = (int) examPaperTikForSchool.stream()
+                        .filter(e -> minValue <= e.getAssignedScore().doubleValue() && maxValue > e.getAssignedScore().doubleValue()).count();
+
+            } else if ("[".equals(minSign) && "]".equals(maxSign)) {
+                colCount = (int) examPaperTikForCollege.stream()
+                        .filter(e -> minValue <= e.getAssignedScore().doubleValue() && maxValue >= e.getAssignedScore().doubleValue()).count();
+                schCount = (int) examPaperTikForSchool.stream()
+                        .filter(e -> minValue <= e.getAssignedScore().doubleValue() && maxValue >= e.getAssignedScore().doubleValue()).count();
+            }
+
+            gradeDistributionList.add(new GradeDistributionResult(colCount, schCount, describe));
+        }
+
+        // 计算分数段分布
+        List<PiecewiseDistributionResult> piecewiseDistributionList = new ArrayList<>();
+        for (PiecewiseScopeEnum value : PiecewiseScopeEnum.values()) {
+            String remark = value.getRemark();
+            String name = value.getName();
+            double colCount = 0;
+            double schCount = 0;
+
+            Map<String, Object> scopeMap = AnalyzeScopeUtil.analyzeScope(value.getScope());
+            String minSign = String.valueOf(scopeMap.get("minSign"));
+            String maxSign = String.valueOf(scopeMap.get("maxSign"));
+            double minValue = Double.parseDouble(String.valueOf(scopeMap.get("minValue")));
+            double maxValue = Double.parseDouble(String.valueOf(scopeMap.get("maxValue")));
+            if ("(".equals(minSign) && ")".equals(maxSign)) {
+                colCount = (int) examPaperTikForCollege.stream()
+                        .filter(e -> minValue < e.getPercentGrade().doubleValue() && maxValue > e.getPercentGrade().doubleValue()).count();
+                schCount = (int) examPaperTikForSchool.stream()
+                        .filter(e -> minValue < e.getPercentGrade().doubleValue() && maxValue > e.getPercentGrade().doubleValue()).count();
+
+            } else if ("(".equals(minSign) && "]".equals(maxSign)) {
+                colCount = (int) examPaperTikForCollege.stream()
+                        .filter(e -> minValue < e.getPercentGrade().doubleValue() && maxValue >= e.getPercentGrade().doubleValue()).count();
+                schCount = (int) examPaperTikForSchool.stream()
+                        .filter(e -> minValue < e.getPercentGrade().doubleValue() && maxValue >= e.getPercentGrade().doubleValue()).count();
+
+            } else if ("[".equals(minSign) && ")".equals(maxSign)) {
+                colCount = (int) examPaperTikForCollege.stream()
+                        .filter(e -> minValue <= e.getPercentGrade().doubleValue() && maxValue > e.getPercentGrade().doubleValue()).count();
+                schCount = (int) examPaperTikForSchool.stream()
+                        .filter(e -> minValue <= e.getPercentGrade().doubleValue() && maxValue > e.getPercentGrade().doubleValue()).count();
+
+            } else if ("[".equals(minSign) && "]".equals(maxSign)) {
+                colCount = (int) examPaperTikForCollege.stream()
+                        .filter(e -> minValue <= e.getPercentGrade().doubleValue() && maxValue >= e.getPercentGrade().doubleValue()).count();
+                schCount = (int) examPaperTikForSchool.stream()
+                        .filter(e -> minValue <= e.getPercentGrade().doubleValue() && maxValue >= e.getPercentGrade().doubleValue()).count();
+            }
+            double colCountRate = MathUtil.formatDouble2(colCount / colTotalCount * 100); //本院比率 保留2位小数
+            double schCountRate = MathUtil.formatDouble2(schCount / schTotalCount * 100); //全校比率 保留2位小数
+
+            piecewiseDistributionList.add(new PiecewiseDistributionResult(name, colCount, colCountRate, schCount, schCountRate, remark));
+        }
+        return new CollegeAndSchoolGradeDistributionResult(gradeDistributionList, piecewiseDistributionList);
+    }
+
+    /**
+     * 学院学科报表查询维度
+     *
+     * @param examId
+     * @param courseCode
+     * @param collegeId
+     * @return
+     */
+    @Override
+    public DimensionAnalyzeResult findDimensionInfo(Long examId, String courseCode, Long collegeId) {
+        //查找维度
+        List<CourseDimensionResult> dimensionInfoDatasource = tbDimensionService.findDimensionInfo(examId, courseCode, collegeId);
+        if (dimensionInfoDatasource.size() < 1) {
+            throw ExceptionResultEnum.DATA_ERROR.exception();
+        }
+        List<ModuleDimensionResult> dimensionAnalyzeList = new ArrayList<>();
+        Set<String> moduleSet = dimensionInfoDatasource.stream().map(e -> e.getModule()).collect(Collectors.toSet()); // 考察模块集合
+        for (String module : moduleSet) {
+            List<CourseDimensionResult> dimensionInfoList = dimensionInfoDatasource
+                    .stream().filter(e -> module.equals(e.getModule())).collect(Collectors.toList());
+
+            List<DimensionInfoResult> dioList = new ArrayList<>();
+            List<DimensionInfoResult> batterThanAll = new ArrayList<>(); // 掌握较好
+            List<DimensionInfoResult> worseThanAll = new ArrayList<>(); // 掌握较差
+            for (CourseDimensionResult courseDimensionResult : dimensionInfoList) {
+                String dimensionCode = String.valueOf(courseDimensionResult.getDimensionCode());
+                String dimensionName = String.valueOf(courseDimensionResult.getDimensionName());
+                double schScoreRate = courseDimensionResult.getSchScoreRate();
+                double colScoreRate = courseDimensionResult.getColScoreRate();
+                if (colScoreRate >= schScoreRate) {
+                    batterThanAll.add(new DimensionInfoResult(dimensionCode, dimensionName));
+                } else {
+                    worseThanAll.add(new DimensionInfoResult(dimensionCode, dimensionName));
+                }
+                dioList.add(new DimensionInfoResult(dimensionCode, dimensionName, String.valueOf(courseDimensionResult.getTotalCount()), String.valueOf(schScoreRate), String.valueOf(colScoreRate)));
+            }
+            dimensionAnalyzeList.add(new ModuleDimensionResult(module, dioList, batterThanAll, worseThanAll));
+        }
+        return new DimensionAnalyzeResult(dimensionAnalyzeList);
+    }
+
+    /**
+     * 查找题目相关
+     *
+     * @param examId
+     * @param courseCode
+     * @param collegeId
+     * @param questionDatasource
+     * @return
+     */
+    @Override
+    public QuestionInfoResult findSituationOfQuestions(Long examId, String courseCode, Long collegeId, List<TBPaperStructResult> questionDatasource) {
+        //查找难易度
+        QueryWrapper<TBCommonLevelConfig> tbCommonLevelConfigQueryWrapper = new QueryWrapper<>();
+        tbCommonLevelConfigQueryWrapper.lambda().eq(TBCommonLevelConfig::getExamId, examId)
+                .eq(TBCommonLevelConfig::getCourseCode, courseCode)
+                .eq(TBCommonLevelConfig::getLevelType, "难度等级");
+        List<TBCommonLevelConfig> configLevelDatasource = tbCommonLevelConfigService.list(tbCommonLevelConfigQueryWrapper);
+        //查找答题记录
+        List<TBAnswerResult> answerDetailDatasource = tbAnswerService.findValidAnswerDetail(examId, courseCode);
+        Set<String> paperTypeList = questionDatasource.stream().map(e -> e.getPaperType()).collect(Collectors.toSet());
+        List<PaperTypeResult> questionInfoList = new ArrayList<>();
+        for (String paperType : paperTypeList) {
+            List<CellResult> cellList = new ArrayList<>();
+            for (TBCommonLevelConfig tbCommonLevelConfig : configLevelDatasource) {
+                String interpret = tbCommonLevelConfig.getInterpret();
+                String scope = tbCommonLevelConfig.getScope();
+
+                Integer count = questionDatasource.parallelStream()
+                        .filter(e -> paperType.equals(e.getPaperType()) && interpret.equals(e.getDifficult()))
+                        .collect(Collectors.toList()).size(); // 题目信息
+                List<TBAnswerResult> answerDetailForSch = answerDetailDatasource.parallelStream()
+                        .filter(e -> paperType.equals(e.getPaperType()) && interpret.equals(e.getDifficult()))
+                        .collect(Collectors.toList());
+                double colAvgScoreRate = answerDetailForSch.parallelStream()
+                        .filter(e -> collegeId.longValue() == e.getCollegeId()).collect(Collectors.toList())
+                        .parallelStream().collect(Collectors.averagingDouble(s -> s.getScoreRate()));
+                double schAvgScoreRate = answerDetailForSch.parallelStream()
+                        .collect(Collectors.averagingDouble(e -> e.getScoreRate()));
+
+                // 得分率保留2位小数处理
+                colAvgScoreRate = MathUtil.formatDouble2(colAvgScoreRate * 100);
+                schAvgScoreRate = MathUtil.formatDouble2(schAvgScoreRate * 100);
+                cellList.add(new CellResult(interpret, scope, colAvgScoreRate, schAvgScoreRate, count));
+            }
+            questionInfoList.add(new PaperTypeResult(paperType, cellList));
+        }
+        return new QuestionInfoResult(questionInfoList);
+    }
+
+    /**
+     * 查找老师信息
+     *
+     * @param examId
+     * @param courseCode
+     * @param collegeId
+     * @return
+     */
+    @Override
+    public TeacherInfoListResult findTeacherInfo(Long examId, String courseCode, Long collegeId) {
+        //查找老师得分
+        List<TAExamCourseTeacherResult> taExamCourseTeacherResultList = taExamCourseCollegeTeacherService.findTeacherInfo(examId, courseCode, collegeId);
+        if (taExamCourseTeacherResultList.size() < 1) {
+            throw ExceptionResultEnum.DATA_ERROR.exception();
+        }
+        return new TeacherInfoListResult(taExamCourseTeacherResultList);
+    }
+
+    /**
+     * 查找题目信息
+     *
+     * @param examId
+     * @param courseCode
+     * @param collegeId
+     * @param questionDatasource
+     * @return
+     */
+    @Override
+    public QuestionListResult findQuestionInfo(Long examId, String courseCode, Long collegeId, List<TBPaperStructResult> questionDatasource) {
+        //查找维度
+        QueryWrapper<TBDimension> tbDimensionQueryWrapper = new QueryWrapper<>();
+        tbDimensionQueryWrapper.lambda().eq(TBDimension::getExamId, examId)
+                .eq(TBDimension::getCourseCode, courseCode);
+        List<TBDimension> dimensionDataSource = tbDimensionService.list(tbDimensionQueryWrapper);
+
+        Set<String> paperTypeSet = questionDatasource.stream().map(e -> e.getPaperType()).collect(Collectors.toSet());
+        List<QuestionResult> questionList = new ArrayList<>();
+        for (String paperType : paperTypeSet) {
+            List<TBPaperStructResult> cellList = questionDatasource.stream()
+                    .filter(e -> paperType.equals(e.getPaperType())).collect(Collectors.toList());
+
+            for (TBPaperStructResult cell : cellList) {
+                cell.setPaperType(null);
+            }
+
+            Set<String> knowledgeDimensionSet = new HashSet<>();
+            for (TBPaperStructResult cell : cellList) {
+                String knowledgeDimension = cell.getKnowledgeDimension();
+                String[] arr = knowledgeDimension.split(",");
+                knowledgeDimensionSet.addAll(Arrays.asList(arr));
+            }
+            List<String> knowledgeDimensionSort = MathUtil.sortDimension(new ArrayList<>(knowledgeDimensionSet)); // 经过特殊排序的知识点集合
+
+            List<DimensionInfoResult> dimensionList = new ArrayList<>();
+            for (String dimensionCode : knowledgeDimensionSort) {
+                String dimensionName = "";
+                List<String> nameTwoList = dimensionDataSource.stream()
+                        .filter(e -> dimensionCode.equals(e.getCodeSecond()))
+                        .map(e -> e.getNameSecond()).collect(Collectors.toList());
+                if (nameTwoList.size() < 1) {
+                    List<String> tmpList = dimensionDataSource.stream()
+                            .filter(e -> dimensionCode.equals(e.getCodePrimary()))
+                            .map(e -> e.getNamePrimary()).collect(Collectors.toList());
+                    if (tmpList.size() == 0) {
+                        continue;
+                    }
+                    dimensionName = tmpList.get(0);
+                } else {
+                    dimensionName = nameTwoList.get(0);
+                }
+
+                dimensionList.add(new DimensionInfoResult(dimensionCode, dimensionName));
+            }
+            questionList.add(new QuestionResult(paperType, cellList, dimensionList));
+
+        }
+        return new QuestionListResult(questionList);
     }
 }

+ 15 - 38
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/service/impl/TAExamCourseServiceImpl.java

@@ -1,6 +1,5 @@
 package com.qmth.teachcloud.report.business.service.impl;
 
-import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
 import com.baomidou.mybatisplus.core.metadata.IPage;
 import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
 import com.qmth.teachcloud.common.entity.SysUser;
@@ -9,8 +8,6 @@ import com.qmth.teachcloud.common.util.ServletUtil;
 import com.qmth.teachcloud.report.business.bean.result.*;
 import com.qmth.teachcloud.report.business.entity.TAExamCourse;
 import com.qmth.teachcloud.report.business.entity.TAExamCourseRecord;
-import com.qmth.teachcloud.report.business.entity.TBCommonLevelConfig;
-import com.qmth.teachcloud.report.business.entity.TBDimension;
 import com.qmth.teachcloud.report.business.enums.PublishStatusEnum;
 import com.qmth.teachcloud.report.business.enums.SemesterEnum;
 import com.qmth.teachcloud.report.business.mapper.TAExamCourseMapper;
@@ -147,47 +144,27 @@ public class TAExamCourseServiceImpl extends ServiceImpl<TAExamCourseMapper, TAE
      * @return
      */
     @Override
-    public List<Object> surveyInspectAnalyseView(Long examId, SemesterEnum semester, String courseCode, Long schoolId) {
+    public CollegeAndCourseResult surveyInspectAnalyseView(Long examId, SemesterEnum semester, String courseCode, Long schoolId) {
         SysUser sysUser = (SysUser) ServletUtil.getRequestUser();
         if (Objects.isNull(sysUser)) {
             throw ExceptionResultEnum.NOT_LOGIN.exception();
         }
-//        //查找试卷
-//        QueryWrapper<TBPaper> tbPaperQueryWrapper = new QueryWrapper<>();
-//        tbPaperQueryWrapper.lambda().eq(TBPaper::getExamId, examId)
-//                .eq(TBPaper::getCourseCode, courseCode);
-//        List<TBPaper> tbPaperList = tbPaperService.list(tbPaperQueryWrapper);
-//
-//        //查找学院科目维度
-//        List<TAExamCourseCollegeInspectResult> taExamCourseCollegeInspectResultList = taExamCourseCollegeInspectService.findCourseDescriptiveStatisticsForCollege(examId, courseCode);
-//        //查找学校科目维度
-//        List<TAExamCourseCollegeInspectResult> taExamCourseSchoolInspectResultList = taExamCourseCollegeInspectService.findCourseDescriptiveStatisticsForSchool(examId, courseCode);
-
+        //学院学科报表查询科目信息
         CourseInfoResult courseInfoResult = reportCommonService.findCourseInfo(examId, courseCode, sysUser.getOrgId());
-        //查找维度
-        List<CourseDimensionResult> courseDimensionResultList = tbDimensionService.findDimensionInfo(examId, courseCode, sysUser.getOrgId());
-
-        //查找难易度
-        QueryWrapper<TBCommonLevelConfig> tbCommonLevelConfigQueryWrapper = new QueryWrapper<>();
-        tbCommonLevelConfigQueryWrapper.lambda().eq(TBCommonLevelConfig::getExamId, examId)
-                .eq(TBCommonLevelConfig::getCourseCode, courseCode)
-                .eq(TBCommonLevelConfig::getLevelType, "难度等级");
-        List<TBCommonLevelConfig> tbCommonLevelConfigList = tbCommonLevelConfigService.list(tbCommonLevelConfigQueryWrapper);
-
+        //学院学科报表科目描述
+        CollegeAndSchoolGradeDistributionResult collegeAndSchoolGradeDistributionResult = reportCommonService.findCourseDistribution(examId, courseCode, sysUser.getOrgId());
+        //学院学科报表维度查询
+        DimensionAnalyzeResult dimensionAnalyzeResult = reportCommonService.findDimensionInfo(examId, courseCode, sysUser.getOrgId());
         //查找试卷结构
-        List<TBPaperStructResult> tbPaperStructList = tbPaperStructService.findQuestionInfo(examId, courseCode);
-
-        //查找答题记录
-        List<TBAnswerResult> tbAnswerResultList = tbAnswerService.findValidAnswerDetail(examId, courseCode);
-
+        List<TBPaperStructResult> questionDatasource = tbPaperStructService.findQuestionInfo(examId, courseCode);
+        //查找题目相关
+        QuestionInfoResult questionInfoResult = reportCommonService.findSituationOfQuestions(examId, courseCode, sysUser.getOrgId(), questionDatasource);
         //查找老师得分
-        List<TAExamCourseTeacherResult> taExamCourseTeacherResultList = taExamCourseCollegeTeacherService.findTeacherInfo(examId, courseCode, sysUser.getOrgId());
-
-        //查找维度
-        QueryWrapper<TBDimension> tbDimensionQueryWrapper = new QueryWrapper<>();
-        tbDimensionQueryWrapper.lambda().eq(TBDimension::getExamId, examId)
-                .eq(TBDimension::getCourseCode, courseCode);
-        List<TBDimension> tbDimensionList = tbDimensionService.list(tbDimensionQueryWrapper);
-        return null;
+        TeacherInfoListResult teacherInfoListResult = reportCommonService.findTeacherInfo(examId, courseCode, sysUser.getOrgId());
+        //查找题目信息
+        QuestionListResult questionListResult = reportCommonService.findQuestionInfo(examId, courseCode, sysUser.getOrgId(), questionDatasource);
+
+        return new CollegeAndCourseResult(courseInfoResult, collegeAndSchoolGradeDistributionResult, dimensionAnalyzeResult,
+                questionInfoResult, teacherInfoListResult, questionListResult);
     }
 }

+ 7 - 0
teachcloud-report-business/src/main/java/com/qmth/teachcloud/report/business/service/impl/TBAnswerServiceImpl.java

@@ -1,6 +1,7 @@
 package com.qmth.teachcloud.report.business.service.impl;
 
 import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
+import com.qmth.teachcloud.report.business.bean.dto.AnswerDetailBean;
 import com.qmth.teachcloud.report.business.bean.dto.query.BasicAnswerDto;
 import com.qmth.teachcloud.report.business.bean.dto.query.ValidAnswerDetailDto;
 import com.qmth.teachcloud.report.business.bean.result.TBAnswerResult;
@@ -10,6 +11,7 @@ import com.qmth.teachcloud.report.business.service.TBAnswerService;
 import org.springframework.stereotype.Service;
 
 import javax.annotation.Resource;
+import java.util.LinkedList;
 import java.util.List;
 
 /**
@@ -47,4 +49,9 @@ public class TBAnswerServiceImpl extends ServiceImpl<TBAnswerMapper, TBAnswer> i
     public List<TBAnswerResult> findValidAnswerDetail(Long examId, String courseCode) {
         return tbAnswerMapper.findValidAnswerDetail(examId, courseCode);
     }
+
+    @Override
+    public LinkedList<AnswerDetailBean> findValidAnswerDetailWithPap(Long examId, String courseCode) {
+        return tbAnswerMapper.findValidAnswerDetailWithPap(examId, courseCode);
+    }
 }

+ 1 - 0
teachcloud-report-business/src/main/resources/mapper/TAExamCourseRecordMapper.xml

@@ -101,6 +101,7 @@
         SELECT
             tbes.ticket_number AS ticketNumber,
             (select so.name from sys_org so where so.id = taecr.inspect_college_id) AS collegeName,
+            taecr.inspect_college_id AS collegeId,
             assigned_score AS assignedScore,
             percent_grade AS percentGrade
         FROM

+ 25 - 1
teachcloud-report-business/src/main/resources/mapper/TBAnswerMapper.xml

@@ -56,7 +56,8 @@
             tik.paper_type AS paperType,
             det.score / tbps.full_score AS scoreRate,
             pap.difficult AS difficult,
-            (select so.name from sys_org so where so.id = tik.inspect_college_id) AS collegeName
+            (select so.name from sys_org so where so.id = tik.inspect_college_id) AS collegeName,
+            tik.inspect_college_id AS collegeId
         FROM
             t_b_answer det
         INNER JOIN t_a_exam_course_record tik ON
@@ -77,4 +78,27 @@
             and tik.absent = 0
         </where>
     </select>
+
+    <select id="findValidAnswerDetailWithPap"
+            resultType="com.qmth.teachcloud.report.business.bean.dto.AnswerDetailBean">
+        SELECT
+            college.id AS collegeId,
+            struct.paper_id AS paperId,
+            record.paper_type AS paperType,
+            answer.score / struct.full_score AS scoreRate,
+            struct.difficult AS difficult,
+            college.name AS collegeName
+        FROM
+            t_b_answer answer
+                INNER JOIN t_a_exam_course_record record ON answer.exam_record_id = record.exam_record_id
+                INNER JOIN t_a_paper_struct struct ON record.paper_id = struct.paper_id
+                INNER JOIN sys_org college ON record.inspect_college_id = college.id
+                AND answer.number_type = struct.number_type
+                AND answer.main_number = struct.big_question_number
+                AND answer.sub_number = struct.small_question_number
+        WHERE
+            record.exam_id = #{examId}
+          AND record.course_code = #{courseCode}
+          AND record.absent = 0 ;
+    </select>
 </mapper>

+ 95 - 91
teachcloud-report/src/main/java/com/qmth/teachcloud/report/api/BasicDatasourceController.java

@@ -102,7 +102,7 @@ public class BasicDatasourceController {
         if (Objects.isNull(file)) {
             throw ExceptionResultEnum.ERROR.exception("找不到附件");
         }
-        if (examId == 0){
+        if (examId == 0) {
             throw ExceptionResultEnum.ERROR.exception("考试id为空");
         }
 
@@ -114,7 +114,7 @@ public class BasicDatasourceController {
         });
 
         //保存到数据库
-        Map<String,Long> paperMap = new HashMap<>();
+        Map<String, Long> paperMap = new HashMap<>();
         List<TBPaper> tbPaperList = new ArrayList<>();
         List<TBPaperStruct> tbPaperStructList = new ArrayList<>();
         if (Objects.nonNull(finalList) && finalList.size() > 0) {
@@ -128,26 +128,26 @@ public class BasicDatasourceController {
 
                         String courseCode = paperConfigDto.getCourseCode();
                         String courseName = paperConfigDto.getCourseName();
-                        if (tbExamCourseService.verifyExamCourseCantRun(examId,schoolId,courseCode,courseName)){
+                        if (tbExamCourseService.verifyExamCourseCantRun(examId, schoolId, courseCode, courseName)) {
                             continue;
                         }
                         BigDecimal coefficient = BigDecimal.ZERO;
-                        if (Objects.nonNull(paperConfigDto.getCoefficient()) && paperConfigDto.getCoefficient() instanceof Double){
+                        if (Objects.nonNull(paperConfigDto.getCoefficient()) && paperConfigDto.getCoefficient() instanceof Double) {
                             coefficient = BigDecimal.valueOf((Double) paperConfigDto.getCoefficient());
                         }
                         String paperType = paperConfigDto.getPaperType();
                         List<TBPaper> oldList = tbPaperService.list(new QueryWrapper<TBPaper>().lambda()
-                                .eq(TBPaper::getExamId,examId).eq(TBPaper::getCourseCode,courseCode).eq(TBPaper::getPaperType,paperType));
+                                .eq(TBPaper::getExamId, examId).eq(TBPaper::getCourseCode, courseCode).eq(TBPaper::getPaperType, paperType));
                         Long id;
-                        if (oldList.size() == 1){
+                        if (oldList.size() == 1) {
                             id = oldList.get(0).getId();
-                        }else if (oldList.size() < 1){
+                        } else if (oldList.size() < 1) {
                             id = SystemConstant.getDbUuid();
-                        }else {
+                        } else {
                             throw ExceptionResultEnum.ERROR.exception("表数据异常[t_b_paper]");
                         }
 
-                        paperMap.put(paperType,id);
+                        paperMap.put(paperType, id);
                         TBPaper tbPaper = new TBPaper();
                         tbPaper.setId(id);
                         tbPaper.setExamId(examId);
@@ -165,7 +165,7 @@ public class BasicDatasourceController {
 
                         String courseCode = paperStructDto.getCourseCode();
                         String courseName = paperStructDto.getCourseName();
-                        if (tbExamCourseService.verifyExamCourseCantRun(examId,schoolId,courseCode,courseName)){
+                        if (tbExamCourseService.verifyExamCourseCantRun(examId, schoolId, courseCode, courseName)) {
                             continue;
                         }
 
@@ -174,7 +174,7 @@ public class BasicDatasourceController {
                         String mainNumber = paperStructDto.getMainNumber();
                         String subNumber = paperStructDto.getSubNumber();
                         String questionType = paperStructDto.getQuestionType();
-                        if (questionType == null){
+                        if (questionType == null) {
                             questionType = "";
                         }
                         String questionName = questionType + " " + mainNumber + SystemConstant.HYPHEN + subNumber;
@@ -201,8 +201,8 @@ public class BasicDatasourceController {
 
         List<Long> paperIdList = tbPaperStructList.stream().map(TBPaperStruct::getPaperId).collect(Collectors.toList());
         // 删除已有的试卷结构数据
-        if (paperIdList.size() > 0){
-            tbPaperStructService.remove(new QueryWrapper<TBPaperStruct>().lambda().in(TBPaperStruct::getPaperId,paperIdList));
+        if (paperIdList.size() > 0) {
+            tbPaperStructService.remove(new QueryWrapper<TBPaperStruct>().lambda().in(TBPaperStruct::getPaperId, paperIdList));
         }
 
         // 批量新增或更新试卷表
@@ -220,7 +220,7 @@ public class BasicDatasourceController {
         if (Objects.isNull(file)) {
             throw ExceptionResultEnum.ERROR.exception("附件不存在");
         }
-        if (schoolId == null || schoolId == 0){
+        if (schoolId == null || schoolId == 0) {
             throw ExceptionResultEnum.ERROR.exception("参数缺失");
         }
         List<LinkedMultiValueMap<Integer, Object>> finalList = ExcelUtil.excelReader(file.getInputStream(),
@@ -249,7 +249,7 @@ public class BasicDatasourceController {
                         String define = moduleProficiencyDto.getProficiency(); // define
                         String courseCode = moduleProficiencyDto.getCourseCode();
                         String courseName = moduleProficiencyDto.getCourseName();
-                        if (tbExamCourseService.verifyExamCourseCantRun(examId,schoolId,courseCode,courseName)){
+                        if (tbExamCourseService.verifyExamCourseCantRun(examId, schoolId, courseCode, courseName)) {
                             continue;
                         }
                         if (proficiencyDegree != null && proficiencyDegree.length() > 0 && define != null && define.length() > 0) {
@@ -313,11 +313,11 @@ public class BasicDatasourceController {
 
                         String courseCode = moduleConfigDto.getCourseCode();
                         String courseName = basicCourseService.getOne(new QueryWrapper<BasicCourse>().lambda()
-                                .eq(BasicCourse::getSchoolId,schoolId).eq(BasicCourse::getCode,courseCode))
+                                .eq(BasicCourse::getSchoolId, schoolId).eq(BasicCourse::getCode, courseCode))
                                 .getName();
 
 
-                        if (tbExamCourseService.verifyExamCourseCantRun(examId,schoolId,courseCode,courseName)){
+                        if (tbExamCourseService.verifyExamCourseCantRun(examId, schoolId, courseCode, courseName)) {
                             continue;
                         }
                         TBModuleConfig tbModuleConfig = new TBModuleConfig();
@@ -355,18 +355,18 @@ public class BasicDatasourceController {
         for (String s : moduleProficiencyRemove) {
             String[] arr = s.split(SystemConstant.HYPHEN);
             tbModuleProficiencyService.remove(new QueryWrapper<TBModuleProficiency>().lambda()
-                    .eq(TBModuleProficiency::getExamId,arr[0])
-                    .eq(TBModuleProficiency::getCourseCode,arr[1])
-                    .eq(TBModuleProficiency::getCourseName,arr[2])
-                    .eq(TBModuleProficiency::getModuleType,arr[3]));
+                    .eq(TBModuleProficiency::getExamId, arr[0])
+                    .eq(TBModuleProficiency::getCourseCode, arr[1])
+                    .eq(TBModuleProficiency::getCourseName, arr[2])
+                    .eq(TBModuleProficiency::getModuleType, arr[3]));
         }
         for (String s : moduleConfigRemove) {
             String[] arr = s.split(SystemConstant.HYPHEN);
             tbModuleConfigService.remove(new QueryWrapper<TBModuleConfig>().lambda()
-                    .eq(TBModuleConfig::getExamId,arr[0])
-                    .eq(TBModuleConfig::getCourseCode,arr[1])
-                    .eq(TBModuleConfig::getCourseName,arr[2])
-                    .eq(TBModuleConfig::getModuleType,arr[3]));
+                    .eq(TBModuleConfig::getExamId, arr[0])
+                    .eq(TBModuleConfig::getCourseCode, arr[1])
+                    .eq(TBModuleConfig::getCourseName, arr[2])
+                    .eq(TBModuleConfig::getModuleType, arr[3]));
         }
         tbModuleProficiencyService.saveBatch(tbModuleProficiencyList);
         tbModuleConfigService.saveBatch(tbModuleConfigList);
@@ -377,11 +377,11 @@ public class BasicDatasourceController {
     @RequestMapping(value = "/dimension/import", method = RequestMethod.POST)
     @Transactional(rollbackFor = Exception.class)
     @ApiResponses({@ApiResponse(code = 200, message = "{\"success\":true}", response = Result.class)})
-    public Result dimensionImport(@ApiParam(value = "上传文件", required = true) @RequestParam MultipartFile file, @RequestParam Long schoolId,@RequestParam Long examId) throws IOException, NoSuchFieldException {
+    public Result dimensionImport(@ApiParam(value = "上传文件", required = true) @RequestParam MultipartFile file, @RequestParam Long schoolId, @RequestParam Long examId) throws IOException, NoSuchFieldException {
         if (Objects.isNull(file)) {
             throw ExceptionResultEnum.ERROR.exception("附件不存在");
         }
-        if (Objects.isNull(schoolId) || schoolId == 0){
+        if (Objects.isNull(schoolId) || schoolId == 0) {
             throw ExceptionResultEnum.ERROR.exception("参数缺失");
         }
         List<LinkedMultiValueMap<Integer, Object>> finalList = ExcelUtil.excelReader(file.getInputStream(), Lists.newArrayList(DimensionDto.class), (finalExcelList, finalColumnNameList, finalExcelErrorList) -> {
@@ -402,10 +402,10 @@ public class BasicDatasourceController {
 
                         String courseCode = dimensionDto.getCourseCode();
                         String courseName = basicCourseService.getOne(new QueryWrapper<BasicCourse>().lambda()
-                                .eq(BasicCourse::getSchoolId,schoolId).eq(BasicCourse::getCode,courseCode))
+                                .eq(BasicCourse::getSchoolId, schoolId).eq(BasicCourse::getCode, courseCode))
                                 .getName();
 
-                        if (tbExamCourseService.verifyExamCourseCantRun(examId,schoolId,courseCode,courseName)){
+                        if (tbExamCourseService.verifyExamCourseCantRun(examId, schoolId, courseCode, courseName)) {
                             continue;
                         }
                         TBDimension tbDimension = new TBDimension();
@@ -429,8 +429,8 @@ public class BasicDatasourceController {
         for (String s : tbDimensionRemove) {
             String[] arr = s.split(SystemConstant.HYPHEN);
             tbDimensionService.remove(new QueryWrapper<TBDimension>().lambda()
-                    .eq(TBDimension::getExamId,arr[0])
-                    .eq(TBDimension::getCourseCode,arr[1]));
+                    .eq(TBDimension::getExamId, arr[0])
+                    .eq(TBDimension::getCourseCode, arr[1]));
         }
         tbDimensionService.saveBatch(tbDimensionList);
         return ResultUtil.ok(Collections.singletonMap(SystemConstant.SUCCESS, true));
@@ -443,15 +443,15 @@ public class BasicDatasourceController {
     public Result examAnswerImport(@ApiParam(value = "云阅卷考试id", required = true) @RequestParam Long id, @ApiParam(value = "云阅卷考试编号", required = false)
     @RequestParam(required = false) String cloudExamCode,
                                    @ApiParam(value = "教研分析将AB卷分开分析时自定义科目和卷形的连接符(连接符必须和’t_e_course‘表中的科目名称中连接符对应)")
-                                   @RequestParam(required = false) String linkSign ,@RequestParam Long schoolId) throws IOException {
-        if (schoolId == null || schoolId == 0){
+                                   @RequestParam(required = false) String linkSign, @RequestParam Long schoolId) throws IOException {
+        if (schoolId == null || schoolId == 0) {
             throw ExceptionResultEnum.ERROR.exception("参数缺失");
         }
         TBExam tbExam = tbExamService.findByCloudExamId(id);
         Long examId = tbExam.getId();
 
         // 该考试要考察的所有课程
-        List<TBExamCourse> tbExamCourseList = tbExamCourseService.list(new QueryWrapper<TBExamCourse>().lambda().eq(TBExamCourse::getExamId,examId));
+        List<TBExamCourse> tbExamCourseList = tbExamCourseService.list(new QueryWrapper<TBExamCourse>().lambda().eq(TBExamCourse::getExamId, examId));
 
         List<Map> finalList = newCallApiService.callStudentScore(id, cloudExamCode);
 //        System.out.println("------------------map : --------------------- \n" + JacksonUtil.parseJson(finalList));
@@ -540,13 +540,13 @@ public class BasicDatasourceController {
                 组建学生基础信息 student
              */
             TBStudent studentTemp = tbStudentService.getOne(new QueryWrapper<TBStudent>().lambda()
-                    .eq(TBStudent::getSchoolId,schoolId)
-                    .eq(TBStudent::getName,name)
-                    .eq(TBStudent::getStudentCode,studentCode));
+                    .eq(TBStudent::getSchoolId, schoolId)
+                    .eq(TBStudent::getName, name)
+                    .eq(TBStudent::getStudentCode, studentCode));
             Long studentId;
-            if (Objects.nonNull(studentTemp)){
+            if (Objects.nonNull(studentTemp)) {
                 studentId = studentTemp.getId();
-            }else {
+            } else {
                 studentId = SystemConstant.getDbUuid();
             }
             TBStudent tbStudent = new TBStudent();
@@ -571,19 +571,20 @@ public class BasicDatasourceController {
                 TBExamCourse tbExamCourse = needDisposeList.get(0);
                 String courseCode = tbExamCourse.getCourseCode();
                 String courseName = tbExamCourse.getCourseName();
-                if (tbExamCourseService.verifyExamCourseCantRun(examId,schoolId,courseCode,courseName)){
+                if (tbExamCourseService.verifyExamCourseCantRun(examId, schoolId, courseCode, courseName)) {
                     continue;
                 }
 
                 // TODO: 2021/6/2 创建学生-考试关系表(全批次删除并新增)
                 // 获取关联的基础表主键
-                SysOrg tbSchoolCollege = sysOrgService.findByForeignKey(schoolId,college,college);
-                TBSchoolClazz tbSchoolClazz = tbSchoolClazzService.findByForeignKey(schoolId,className,className);
-                SysUser tbSchoolTeacher = sysUserService.findByForeignKey(schoolId,teacher,teacher);
+                SysOrg tbSchoolCollege = sysOrgService.findByForeignKey(schoolId, college, college);
+                TBSchoolClazz tbSchoolClazz = tbSchoolClazzService.findByForeignKey(schoolId, className, className);
+                SysUser tbSchoolTeacher = sysUserService.findByForeignKey(schoolId, teacher, teacher);
 
                 TBExamStudent tbExamStudent = new TBExamStudent();
                 Long examStudentId = SystemConstant.getDbUuid();
                 tbExamStudent.setId(examStudentId);
+                tbExamStudent.setSchoolId(tbExamService.getById(examId).getSchoolId());
                 tbExamStudent.setExamId(examId);
                 tbExamStudent.setName(name);
                 tbExamStudent.setStudentId(studentId);
@@ -607,7 +608,7 @@ public class BasicDatasourceController {
                 TBExamRecord tbExamRecord = new TBExamRecord();
                 tbExamRecord.setId(examRecordId);
                 tbExamRecord.setExamId(examId);
-                tbExamRecord.setPaperId(tbPaperService.findByForeignKey(examId,courseCode,courseName,paperType).getId());
+                tbExamRecord.setPaperId(tbPaperService.findByForeignKey(examId, courseCode, courseName, paperType).getId());
                 tbExamRecord.setPaperType(paperType);
                 tbExamRecord.setExamStudentId(examStudentId);
                 tbExamRecord.setSubjectiveScore(BigDecimal.valueOf(Double.parseDouble(subjectiveScore)));
@@ -659,23 +660,23 @@ public class BasicDatasourceController {
         for (String s : courseInfoList) {
             String[] arr = s.split(SystemConstant.HYPHEN);
             Set<Long> ids = tbExamStudentService.list(new QueryWrapper<TBExamStudent>().lambda()
-                    .eq(TBExamStudent::getCourseCode,arr[0])
-                    .eq(TBExamStudent::getCourseName,arr[1]))
+                    .eq(TBExamStudent::getCourseCode, arr[0])
+                    .eq(TBExamStudent::getCourseName, arr[1]))
                     .stream().map(TBExamStudent::getId).collect(Collectors.toSet());
             examStudentRemoveIdSet.addAll(ids);
         }
 
-        if (examStudentRemoveIdSet.size() > 0){
+        if (examStudentRemoveIdSet.size() > 0) {
             // 删除考生表
             tbExamStudentService.removeByIds(examStudentRemoveIdSet);
             List<TBExamRecord> willRemoveRecord = tbExamRecordService.list(new QueryWrapper<TBExamRecord>()
-                    .lambda().in(TBExamRecord::getExamStudentId,examStudentRemoveIdSet));
-            if (willRemoveRecord.size() > 0){
+                    .lambda().in(TBExamRecord::getExamStudentId, examStudentRemoveIdSet));
+            if (willRemoveRecord.size() > 0) {
                 List<Long> willRemoveRecordIdList = willRemoveRecord.stream().map(TBExamRecord::getId).collect(Collectors.toList());
                 // 删除考生作答
                 tbExamRecordService.removeByIds(willRemoveRecordIdList);
                 // 删除考生作答
-                tbAnswerService.remove(new QueryWrapper<TBAnswer>().lambda().in(TBAnswer::getExamRecordId,willRemoveRecordIdList));
+                tbAnswerService.remove(new QueryWrapper<TBAnswer>().lambda().in(TBAnswer::getExamRecordId, willRemoveRecordIdList));
             }
         }
 
@@ -690,40 +691,40 @@ public class BasicDatasourceController {
     @RequestMapping(value = "/special/assignScore", method = RequestMethod.POST)
     @Transactional(rollbackFor = Exception.class)
     @ApiResponses({@ApiResponse(code = 200, message = "{\"success\":true}", response = Result.class)})
-    public Result specialAssignScore(@ApiParam(value = "上传文件", required = true) @RequestParam MultipartFile file, @RequestParam Long examId,@RequestParam Long schoolId,
+    public Result specialAssignScore(@ApiParam(value = "上传文件", required = true) @RequestParam MultipartFile file, @RequestParam Long examId, @RequestParam Long schoolId,
                                      @ApiParam(value = "该Excel中包含多科目赋分时,各科目编号用','隔开", required = true) @RequestParam String courseCodeS) throws IOException, NoSuchFieldException {
 
         List<String> courseCodeList = Arrays.asList(courseCodeS.split(","));
         // 数据同步操作
         // 获取当前课程下所有学生考试成绩记录
-        List<BasicExamRecordDto> basicExamRecordDtoDatasource = tbExamRecordService.findByExamIdAndCourseCodeS(examId,courseCodeList);
+        List<BasicExamRecordDto> basicExamRecordDtoDatasource = tbExamRecordService.findByExamIdAndCourseCodeS(examId, courseCodeList);
         Set<TAExamCourseRecord> taExamCourseRecordDatasource = new HashSet<>();
         for (String s : courseCodeList) {
-            if (tbExamCourseService.verifyExamCourseCantRun(examId,schoolId,s,basicCourseService.findByCourseCode(s).getName())){
+            if (tbExamCourseService.verifyExamCourseCantRun(examId, schoolId, s, basicCourseService.findByCourseCode(s).getName())) {
                 throw ExceptionResultEnum.ERROR.exception("课程编号[" + s + "]的课程分析数据已测试或发布,不能变更基础数据");
             }
             List<BasicExamRecordDto> basicExamRecordDtoList = basicExamRecordDtoDatasource.stream()
                     .filter(e -> s.equals(e.getCourseCode())).collect(Collectors.toList());
-            if (basicExamRecordDtoList.size() > 0){
+            if (basicExamRecordDtoList.size() > 0) {
                 // 删除源数据
                 taExamCourseRecordService.remove(new QueryWrapper<TAExamCourseRecord>()
-                        .lambda().eq(TAExamCourseRecord::getExamId,examId).eq(TAExamCourseRecord::getCourseCode,s));
+                        .lambda().eq(TAExamCourseRecord::getExamId, examId).eq(TAExamCourseRecord::getCourseCode, s));
                 // 迁移数据至't_a_exam_course_record'
                 List<TAExamCourseRecord> taExamCourseRecordList = new ArrayList<>();
                 for (BasicExamRecordDto basicExamRecordDto : basicExamRecordDtoList) {
                     // 正常公式赋分操作
                     Long paperId = basicExamRecordDto.getPaperId();
                     TBPaper tbPaper = tbPaperService.getById(paperId);
-                    if (Objects.isNull(tbPaper)){
+                    if (Objects.isNull(tbPaper)) {
                         throw ExceptionResultEnum.ERROR.exception("试卷信息数据异常");
                     }
                     BigDecimal fullScore = tbPaper.getTotalScore();
                     BigDecimal myScore = basicExamRecordDto.getTotalScore();
                     BigDecimal coefficient = tbPaper.getCoefficient();
                     BigDecimal assignScore;
-                    if (coefficient != null && coefficient.compareTo(BigDecimal.ZERO) > 0){
-                        assignScore = myScore.add(fullScore.subtract(myScore).divide(coefficient,0,BigDecimal.ROUND_HALF_DOWN));
-                    }else {
+                    if (coefficient != null && coefficient.compareTo(BigDecimal.ZERO) > 0) {
+                        assignScore = myScore.add(fullScore.subtract(myScore).divide(coefficient, 0, BigDecimal.ROUND_HALF_DOWN));
+                    } else {
                         assignScore = myScore;
                     }
 
@@ -731,8 +732,9 @@ public class BasicDatasourceController {
                     taExamCourseRecord.setId(SystemConstant.getDbUuid());
                     taExamCourseRecord.setExamRecordId(basicExamRecordDto.getTbExamRecordId());
                     // 数据同步默认赋分成绩为卷面成绩
+                    taExamCourseRecord.setSchoolId(tbExamService.getById(examId).getSchoolId());
                     taExamCourseRecord.setAssignedScore(assignScore);
-                    taExamCourseRecord.setExamId(basicExamRecordDto.getExamId());
+                    taExamCourseRecord.setExamId(examId);
                     taExamCourseRecord.setCourseCode(basicExamRecordDto.getCourseCode());
                     taExamCourseRecord.setPaperId(basicExamRecordDto.getPaperId());
                     taExamCourseRecord.setPaperType(basicExamRecordDto.getPaperType());
@@ -770,7 +772,7 @@ public class BasicDatasourceController {
                     if (assignList.get(y) instanceof AssignDto) {
                         AssignDto assignDto = (AssignDto) assignList.get(y);
                         Long assExamId = Long.parseLong(assignDto.getExamId());
-                        if (!examId.equals(assExamId)){
+                        if (!examId.equals(assExamId)) {
                             throw ExceptionResultEnum.ERROR.exception("excel考试数据异常");
                         }
                         String assCourseCodeS = assignDto.getPaperCodeS();
@@ -781,7 +783,7 @@ public class BasicDatasourceController {
                             List<TAExamCourseRecord> taExamCourseRecordList = taExamCourseRecordDatasource.stream()
                                     .filter(e -> assExamId.equals(e.getExamId()) && s.equals(e.getCourseCode()) && assStudentCode.equals(e.getStudentCode()))
                                     .collect(Collectors.toList());
-                            if (taExamCourseRecordList.size() != 1){
+                            if (taExamCourseRecordList.size() != 1) {
                                 System.out.println("-----------------------");
                                 System.out.println(JSON.toJSONString(taExamCourseRecordList));
                                 throw ExceptionResultEnum.ERROR.exception("赋分异常,考生记录分析表数据异常");
@@ -804,29 +806,30 @@ public class BasicDatasourceController {
     @ApiResponses({@ApiResponse(code = 200, message = "{\"success\":true}", response = Result.class)})
     public Result configImport(@RequestParam Long schoolId, @RequestParam Long examId, @RequestParam String courseCode) {
         String courseName = basicCourseService.findByCourseCode(courseCode).getName();
-        if (tbExamCourseService.verifyExamCourseCantRun(examId,schoolId,courseCode,courseName)){
+        if (tbExamCourseService.verifyExamCourseCantRun(examId, schoolId, courseCode, courseName)) {
             throw ExceptionResultEnum.ERROR.exception("课程编号[" + courseCode + "]的课程分析数据已测试或发布,不能变更基础数据");
         }
-        tbCommonLevelConfigService.importLevelConfig(examId,courseCode,courseName);
-        tbCommonRankLevelConfigService.importRankLevelConfig(examId,courseCode,courseName);
+        tbCommonLevelConfigService.importLevelConfig(examId, courseCode, courseName);
+        tbCommonRankLevelConfigService.importRankLevelConfig(examId, courseCode, courseName);
         return ResultUtil.ok(Collections.singletonMap(SystemConstant.SUCCESS, true));
     }
 
     /**
      * 更新或新增专业信息
+     *
      * @param tbSchoolMajorDtoList 基础专业数据源
      */
-    private void saveMajorInfo(List<TBSchoolMajorDto> tbSchoolMajorDtoList){
+    private void saveMajorInfo(List<TBSchoolMajorDto> tbSchoolMajorDtoList) {
         List<TBSchoolMajor> tbSchoolMajorList = new ArrayList<>();
         for (TBSchoolMajorDto tbSchoolMajorDto : tbSchoolMajorDtoList) {
             TBSchoolMajor old = tbSchoolMajorService.getOne(new QueryWrapper<TBSchoolMajor>().lambda()
-                    .eq(TBSchoolMajor::getSchoolId,tbSchoolMajorDto.getSchoolId())
-                    .eq(TBSchoolMajor::getMajorCode,tbSchoolMajorDto.getMajorCode())
-                    .eq(TBSchoolMajor::getMajorName,tbSchoolMajorDto.getMajorName()));
+                    .eq(TBSchoolMajor::getSchoolId, tbSchoolMajorDto.getSchoolId())
+                    .eq(TBSchoolMajor::getMajorCode, tbSchoolMajorDto.getMajorCode())
+                    .eq(TBSchoolMajor::getMajorName, tbSchoolMajorDto.getMajorName()));
             Long id;
-            if (Objects.nonNull(old)){
+            if (Objects.nonNull(old)) {
                 id = old.getId();
-            }else {
+            } else {
                 id = SystemConstant.getDbUuid();
             }
 
@@ -845,19 +848,20 @@ public class BasicDatasourceController {
 
     /**
      * 更新或新增班级信息
+     *
      * @param tbSchoolClazzDtoList 基础班级数据源
      */
-    private void saveClazzInfo(List<TBSchoolClazzDto> tbSchoolClazzDtoList){
+    private void saveClazzInfo(List<TBSchoolClazzDto> tbSchoolClazzDtoList) {
         List<TBSchoolClazz> tbSchoolClazzList = new ArrayList<>();
         for (TBSchoolClazzDto tbSchoolClazzDto : tbSchoolClazzDtoList) {
             TBSchoolClazz old = tbSchoolClazzService.getOne(new QueryWrapper<TBSchoolClazz>().lambda()
-                    .eq(TBSchoolClazz::getSchoolId,tbSchoolClazzDto.getSchoolId())
-                    .eq(TBSchoolClazz::getClazzCode,tbSchoolClazzDto.getClazzCode())
-                    .eq(TBSchoolClazz::getClazzName,tbSchoolClazzDto.getClazzName()));
+                    .eq(TBSchoolClazz::getSchoolId, tbSchoolClazzDto.getSchoolId())
+                    .eq(TBSchoolClazz::getClazzCode, tbSchoolClazzDto.getClazzCode())
+                    .eq(TBSchoolClazz::getClazzName, tbSchoolClazzDto.getClazzName()));
             Long id;
-            if (Objects.nonNull(old)){
+            if (Objects.nonNull(old)) {
                 id = old.getId();
-            }else {
+            } else {
                 id = SystemConstant.getDbUuid();
             }
 
@@ -876,19 +880,20 @@ public class BasicDatasourceController {
 
     /**
      * 更新或新增学院信息
+     *
      * @param tbSchoolCollegeDtoList 基础学院数据源
      */
-    private void saveCollegeInfo(List<TBSchoolCollegeDto> tbSchoolCollegeDtoList){
+    private void saveCollegeInfo(List<TBSchoolCollegeDto> tbSchoolCollegeDtoList) {
         List<SysOrg> sysOrgList = new ArrayList<>();
         for (TBSchoolCollegeDto tbSchoolCollegeDto : tbSchoolCollegeDtoList) {
             SysOrg old = sysOrgService.getOne(new QueryWrapper<SysOrg>().lambda()
-                    .eq(SysOrg::getSchoolId,tbSchoolCollegeDto.getSchoolId())
-                    .eq(SysOrg::getCode,tbSchoolCollegeDto.getCollegeCode())
-                    .eq(SysOrg::getName,tbSchoolCollegeDto.getCollegeName()));
+                    .eq(SysOrg::getSchoolId, tbSchoolCollegeDto.getSchoolId())
+                    .eq(SysOrg::getCode, tbSchoolCollegeDto.getCollegeCode())
+                    .eq(SysOrg::getName, tbSchoolCollegeDto.getCollegeName()));
             Long id;
-            if (Objects.nonNull(old)){
+            if (Objects.nonNull(old)) {
                 id = old.getId();
-            }else {
+            } else {
                 id = SystemConstant.getDbUuid();
             }
 
@@ -905,17 +910,17 @@ public class BasicDatasourceController {
 
     /**
      * 更新或新增教师信息
+     *
      * @param tbSchoolTeacherDtoList 基础教师数据源
      */
-    private void saveTeacherInfo(List<TBSchoolTeacherDto> tbSchoolTeacherDtoList){
-        List<SysUser> tbSchoolTeacherList = new ArrayList<>();
+    private void saveTeacherInfo(List<TBSchoolTeacherDto> tbSchoolTeacherDtoList) {
         for (TBSchoolTeacherDto tbSchoolTeacherDto : tbSchoolTeacherDtoList) {
             SysUser old = sysUserService.getOne(new QueryWrapper<SysUser>().lambda()
-                    .eq(SysUser::getSchoolId,tbSchoolTeacherDto.getSchoolId())
-                    .eq(SysUser::getLoginName,tbSchoolTeacherDto.getTeacherCode())
-                    .eq(SysUser::getRealName,tbSchoolTeacherDto.getTeacherName()));
+                    .eq(SysUser::getSchoolId, tbSchoolTeacherDto.getSchoolId())
+                    .eq(SysUser::getLoginName, tbSchoolTeacherDto.getTeacherCode())
+                    .eq(SysUser::getRealName, tbSchoolTeacherDto.getTeacherName()));
             Long id = 0L;
-            if (Objects.nonNull(old)){
+            if (Objects.nonNull(old)) {
                 id = old.getId();
             }
             SysRole teacherRole = sysRoleService.list(new QueryWrapper<SysRole>().lambda().eq(SysRole::getType, RoleTypeEnum.TEACHER)).get(0);
@@ -923,7 +928,7 @@ public class BasicDatasourceController {
             roleIds.add(teacherRole.getId());
 
             UserSaveParams userSaveParams = new UserSaveParams();
-            if (id > 0){
+            if (id > 0) {
                 userSaveParams.setId(id);
             }
 
@@ -938,5 +943,4 @@ public class BasicDatasourceController {
             sysUserService.save(userSaveParams);
         }
     }
-
 }

+ 1 - 1
teachcloud-report/src/main/java/com/qmth/teachcloud/report/api/CourseController.java

@@ -44,7 +44,7 @@ public class CourseController {
                                            @ApiParam(value = "科目编码", required = true) @RequestParam String courseCode,
                                            @ApiParam(value = "学校id", required = true) @RequestParam String schoolId) {
 
-        return ResultUtil.ok();
+        return ResultUtil.ok(taExamCourseService.surveyInspectAnalyseView(SystemConstant.convertIdToLong(examId), semester, courseCode, SystemConstant.convertIdToLong(schoolId)));
     }
 
     @ApiOperation(value = "赋分管理列表接口")

+ 26 - 12
teachcloud-report/src/test/java/com/qmth/teachcloud/report/AnalyzeForStudentServiceTest.java

@@ -1,6 +1,6 @@
 package com.qmth.teachcloud.report;
 
-import com.qmth.teachcloud.report.business.service.AnalyzeForStudentService;
+import com.qmth.teachcloud.report.business.service.AnalyzeForReportService;
 import org.junit.Test;
 import org.junit.runner.RunWith;
 import org.springframework.boot.test.context.SpringBootTest;
@@ -17,12 +17,12 @@ import javax.annotation.Resource;
 @RunWith(SpringRunner.class)
 public class AnalyzeForStudentServiceTest {
     @Resource
-    private AnalyzeForStudentService analyzeForStudentService;
+    private AnalyzeForReportService analyzeForReportService;
     @Test
     public void buildAnalyzeExamCourse() {
         Long examId = 1L;
         String courseCode = "1013";
-        System.out.println(analyzeForStudentService.buildAnalyzeExamCourse(examId,courseCode));
+        System.out.println(analyzeForReportService.buildAnalyzeExamCourse(examId,courseCode));
 
     }
 
@@ -30,61 +30,75 @@ public class AnalyzeForStudentServiceTest {
     public void buildAnalyzeExamCourseRecord() {
         Long examId = 1L;
         String courseCode = "1013";
-        System.out.println(analyzeForStudentService.buildAnalyzeExamCourseRecord(examId,courseCode));
+        System.out.println(analyzeForReportService.buildAnalyzeExamCourseRecord(examId,courseCode));
     }
 
     @Test
     public void buildAnalyzeExamCourseCollegeInspectByOther() {
         Long examId = 1L;
         String courseCode = "1013";
-        System.out.println(analyzeForStudentService.buildAnalyzeExamCourseCollegeInspect(examId,courseCode));
+        System.out.println(analyzeForReportService.buildAnalyzeExamCourseCollegeInspect(examId,courseCode));
     }
 
     @Test
     public void buildAnalyzeExamCourseClazz() {
         Long examId = 1L;
         String courseCode = "1013";
-        System.out.println(analyzeForStudentService.buildAnalyzeExamCourseClazz(examId,courseCode));
+        System.out.println(analyzeForReportService.buildAnalyzeExamCourseClazz(examId,courseCode));
     }
 
     @Test
     public void analyzePointScoreRate() throws Exception {
         Long examId = 1L;
         String courseCode = "1013";
-        analyzeForStudentService.AnalyzePointScoreRate(examId,courseCode);
+        analyzeForReportService.AnalyzePointScoreRate(examId,courseCode);
     }
 
     @Test
     public void buildAnalyzeExamCourseCollegeInspectDio() {
         Long examId = 1L;
         String courseCode = "1013";
-        System.out.println(analyzeForStudentService.buildAnalyzeExamCourseCollegeInspectDio(examId,courseCode));
+        System.out.println(analyzeForReportService.buildAnalyzeExamCourseCollegeInspectDio(examId,courseCode));
     }
 
     @Test
     public void buildAnalyzePaperStruct() {
         Long examId = 1L;
         String courseCode = "1013";
-        System.out.println(analyzeForStudentService.buildAnalyzePaperStruct(examId,courseCode));
+        System.out.println(analyzeForReportService.buildAnalyzePaperStruct(examId,courseCode));
+    }
+
+    @Test
+    public void buildExamPaperDifficult(){
+        Long examId = 1L;
+        String courseCode = "1013";
+        System.out.println(analyzeForReportService.buildExamPaperDifficult(examId,courseCode));
     }
 
     @Test
     public void buildAnalyzeExamTotal() {
         Long examId = 1L;
-        System.out.println(analyzeForStudentService.buildAnalyzeExamTotal(examId));
+        System.out.println(analyzeForReportService.buildAnalyzeExamTotal(examId));
     }
 
     @Test
     public void buildAnalyzeExamCourseCollegeTeacher() {
         Long examId = 1L;
         String courseCode = "1013";
-        System.out.println(analyzeForStudentService.buildAnalyzeExamCourseCollegeTeacher(examId,courseCode));
+        System.out.println(analyzeForReportService.buildAnalyzeExamCourseCollegeTeacher(examId,courseCode));
     }
 
     @Test
     public void buildAnalyzeExamCourseTeacher() {
         Long examId = 1L;
         String courseCode = "1013";
-        System.out.println(analyzeForStudentService.buildAnalyzeExamCourseTeacher(examId,courseCode));
+        System.out.println(analyzeForReportService.buildAnalyzeExamCourseTeacher(examId,courseCode));
+    }
+
+    @Test
+    public void finishCalculate(){
+        Long examId = 1L;
+        String courseCode = "1013";
+        System.out.println(analyzeForReportService.finishCalculate(examId,courseCode));
     }
 }