package com.xhkjedu.smarking.service.paper;

import com.alibaba.fastjson.JSON;
import com.xhkjedu.smarking.mapper.paper.MsPaperAnalyzeMapper;
import com.xhkjedu.smarking.mapper.paper.MsPaperQtypeMapper;
import com.xhkjedu.smarking.mapper.paper.MsPaperQtypeQuestionMapper;
import com.xhkjedu.smarking.mapper.paper.MsPaperQtypeQuestionPointMapper;
import com.xhkjedu.smarking.model.paper.MsPaper;
import com.xhkjedu.smarking.model.paper.MsPaperAnalyze;
import com.xhkjedu.smarking.model.paper.MsPaperQtypeQuestion;
import com.xhkjedu.smarking.model.paper.MsPaperQtypeQuestionPoint;
import com.xhkjedu.smarking.vo.paper.*;
import com.xhkjedu.utils.N_Utils;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.util.*;
import java.util.stream.Collectors;

/**
 * @Description：试卷分析
 * @Author: WN
 * @Date: 2025/1/2 17:01:04
 **/
@Service
public class MsPaperAnalyzeService {
    @Resource
    private MsPaperQtypeMapper msPaperQtypeMapper;
    @Resource
    private MsPaperQtypeQuestionMapper msPaperQtypeQuestionMapper;
    @Resource
    private MsPaperQtypeQuestionPointMapper msPaperQtypeQuestionPointMapper;
    @Resource
    private MsPaperAnalyzeMapper msPaperAnalyzeMapper;

    // 保存试卷分析--题库
    public void savePaperAnalyzeForQuestion(MsPaper paper) {
        Integer mpid = paper.getMpid();

        // 总体分析（主观题、客观题）
        List<MsPaperQtypeVo> qtypelist = msPaperQtypeMapper.listPaperQtypeQuestions(paper.getMpid());// 试卷题型试题信息
        List<MsPaperQtypeQuestion> uplist = new ArrayList<>();// 改试卷中客观题选项数量
        List<MsPaperQtypeQuestion> upComplexitylist = new ArrayList<>();// 改试卷中客观题难易度
        List<MsPaperQtypeQuestionPoint> upQpointlist = new ArrayList<>();// 保存试卷中试题知识点关联关系

        List<QuestionOrderVo> pointqlist = new ArrayList<>();// 用于存放知识点，以及知识点下得分
        List<MsPaperQtypeQuestionVo> mquestions = new ArrayList<>();// 存放单题和母题
        List<QuestionOrderVo> complexitylist = new ArrayList<>();// 试题难易度存放试题
        List<QuestionPointVo> quesplist = new ArrayList<>();// 单题、母题对应知识点

        // 处理出试卷中所有试题、知识点
        List<Map<String, Object>> typelist = new ArrayList<>();// 题型分析
        for (MsPaperQtypeVo qt : qtypelist) {
            List<Integer> qorderlist = new ArrayList<>();
            List<QuestionOrderVo> qtypeqlist = new ArrayList<>();
            List<MsPaperQtypeQuestionVo> tqlist = qt.getQuestions();
            int hasmt = 0;
            for (MsPaperQtypeQuestionVo q : tqlist) {
                int ctype = q.getCtype();
                // 单题的pid设置为默认值，方便后续进行单题和母题处理
                if (q.getQlevel() == 1) {
                    q.setQuestionpid("000");
                    // 判断试题是否是客观题
                    if (N_Utils.isObjectiveQuestion(ctype)) {
                        // 判断试题是否是客观题,暂时用mctype进行标识
                        q.setMctype(111);
                    } else {
                        q.setMctype(112);
                    }
                    // 设置知识点
                    mquestions.add(q);
                    // 获取试题知识点
                    List<Map<String, Object>> qpoints = q.getPoints();
                    // 处理试题知识点占分
                    setPaperQuestionPointScore(pointqlist, quesplist, qpoints, q, null,null, null);
                    setPaperQuestionPointRelation(qpoints, q, null, upQpointlist, mpid);
                    setPaperQuestionQtypeScore(qtypeqlist, q, null, null);// 处理试题题型
                    setPaperQuestionComplexityScore(complexitylist, q, null, null, upComplexitylist);// 处理试题难易度

                }
                if (q.getQlevel() == 3) {
                    hasmt++;
                }
                if (!qorderlist.contains(q.getQorder())) {
                    qorderlist.add(q.getQorder());
                }
                // 为了处理客观题中选项数量
                if (ctype == 1 || ctype == 2 || ctype == 4 || ctype == 5 || ctype == 6) {
                    List<String> strlst = JSON.parseArray(q.getQoption(), String.class);
                    MsPaperQtypeQuestion eqq = new MsPaperQtypeQuestion();
                    eqq.setMptqid(q.getMptqid());
                    eqq.setOptionnum(strlst.size());
                    uplist.add(eqq);
                }
            }

            if (hasmt > 0) {
                // 说明该题型下有复合题,复合体进行知识点、题型下试题题号及id进行操作
                LinkedHashMap<String, List<MsPaperQtypeQuestionVo>> quesMap = tqlist.stream().collect(Collectors.groupingBy(MsPaperQtypeQuestionVo::getQuestionpid,
                                                                                                                            LinkedHashMap::new, Collectors.toList()));
                for (Map.Entry<String, List<MsPaperQtypeQuestionVo>> entry : quesMap.entrySet()) {
                    if (!entry.getKey().equals("000")) {
                        // 说明该题为母题，
                        MsPaperQtypeQuestionVo mq = new MsPaperQtypeQuestionVo();
                        List<MsPaperQtypeQuestionVo> sonques = entry.getValue();
                        int k = 0;// 如果k大于1说明有小题是主观题，则母题为主观题
                        double score = 0;
                        for (MsPaperQtypeQuestionVo sq : sonques) {
                            if (!N_Utils.isObjectiveQuestion(sq.getCtype())) {
                                k++;
                            }
                            score = N_Utils.getDoubleSum(score, sq.getQscore());
                        }

                        MsPaperQtypeQuestionVo qobj = sonques.get(0);
                        mq.setQuestionid(qobj.getQuestionpid());
                        mq.setComplexity(qobj.getMcomplexity());
                        mq.setQorder(qobj.getQorder());
                        mq.setQscore(score);
                        mq.setQtypename(qobj.getMqtypename());
                        if (k == 0) {
                            mq.setMctype(111);
                        } else {
                            mq.setMctype(112);
                        }
                        mq.setQlevel(qobj.getMqlevel());
                        mq.setSonques(sonques);
                        // 获取所有子题的试题题号
                        String[] qnstr = sonques.stream().map(MsPaperQtypeQuestionVo::getQn).toArray(String[]::new);
                        String[] qnstrStr = sonques.stream().map(MsPaperQtypeQuestionVo::getQnstr).toArray(String[]::new);
                        // 所有子题的试题eptqid
                        List<Integer> eptqids = sonques.stream().map(MsPaperQtypeQuestionVo::getMptqid).collect(Collectors.toList());
                        Integer[] eptqidstr = eptqids.toArray(new Integer[0]);

                        // 获取知识点
                        List<Map<String, Object>> qpoints = sonques.get(0).getPoints();
                        mq.setPoints(qpoints);
                        mquestions.add(mq);
                        setPaperQuestionPointScore(pointqlist, quesplist, qpoints, mq, qnstr,qnstrStr, eptqids);
                        setPaperQuestionPointRelation(qpoints, mq, eptqids, upQpointlist, mpid);
                        setPaperQuestionQtypeScore(qtypeqlist, mq, qnstr, eptqidstr);// 处理试题题型
                        setPaperQuestionComplexityScore(complexitylist, mq, qnstr, eptqidstr, upComplexitylist);// 处理试题难易度
                    }
                }
            }

            // 试题题型分析数据
            double storerate = N_Utils.getDoubleDivideAndMulitiply(qt.getMptscore(), paper.getPscore());
            Map<String, Object> tmap = new TreeMap<>();
            tmap.put("qtid", qt.getMptid());
            tmap.put("qtname", qt.getMptname());
            tmap.put("num", qt.getMptnum());
            tmap.put("score", qt.getMptscore());
            tmap.put("srate", storerate);
            qtypeqlist = qtypeqlist.stream().sorted(Comparator.comparing(QuestionOrderVo::getOrder)).collect(Collectors.toList());
            tmap.put("ques", qtypeqlist);
            typelist.add(tmap);
        }

        // 进行客观题选项处理
        if (N_Utils.isListNotEmpty(uplist)) {
            msPaperQtypeQuestionMapper.updateBatchQuestionOptionnum(uplist);
        }

        // 试题总体分布进行分析
        // 客观题集合
        List<MsPaperQtypeQuestionVo> ktlst = mquestions.stream().filter(q -> q.getMctype() == 111).collect(Collectors.toList());
        int ktnum = ktlst.size();
        double ktscore = ktlst.stream().mapToDouble(MsPaperQtypeQuestionVo::getQscore).sum();
        double ktnrate = N_Utils.getIntegerDivideAndMulitiply(ktnum, paper.getPnum());
        double ktsrate = N_Utils.getDoubleDivideAndMulitiply(ktscore, paper.getPscore());
        List<MsPaperQsVo> ranglist = new ArrayList<>();
        ranglist.add(new MsPaperQsVo("客观题", ktscore, ktnum, ktsrate, ktnrate));
        MsPaperQsVo zgq = new MsPaperQsVo();
        zgq.setQtname("主观题");
        zgq.setNum(paper.getPnum() - ktnum);
        zgq.setNrate(N_Utils.getDoubleReduce(100.0, ktnrate));
        zgq.setScore(N_Utils.getDoubleReduce(paper.getPscore(), ktscore));
        zgq.setSrate(N_Utils.getDoubleReduce(100.0, ktsrate));
        ranglist.add(zgq);
        Map<String, Object> ztmap = new TreeMap<>();
        ztmap.put("pnum", paper.getPnum());
        ztmap.put("pscore", paper.getPscore());
        ztmap.put("ranglist", ranglist);

        // 设置试卷中试题难易度
        msPaperQtypeQuestionMapper.updateBatchQuestionComplexity(upComplexitylist);

        // 难易度
        List<Map<String, Object>> clist = new ArrayList<>();
        if (N_Utils.isListNotEmpty(complexitylist)) {
            Map<String, List<QuestionOrderVo>> complxmap = complexitylist.stream().collect(Collectors.groupingBy(QuestionOrderVo::getId, Collectors.toList()));
            for (Map.Entry<String, List<QuestionOrderVo>> entry : complxmap.entrySet()) {
                List<QuestionOrderVo> pgblist = entry.getValue();
                Double score = pgblist.stream().mapToDouble(QuestionOrderVo::getScore).sum();
                score = N_Utils.formatDouble(score, 1);
                Double srate = N_Utils.getDoubleDivideAndMulitiply(score, paper.getPscore());
                Map<String, Object> prate = new TreeMap<>();
                prate.put("level", Integer.parseInt(entry.getKey()));
                prate.put("score", score);
                prate.put("srate", srate);
                prate.put("ques", pgblist.stream().sorted(Comparator.comparing(QuestionOrderVo::getOrder)).collect(Collectors.toList()));
                clist.add(prate);
            }
        }

        // 保存试卷试题知识点关系
        msPaperQtypeQuestionPointMapper.deleteByMpid(mpid);
        msPaperQtypeQuestionPointMapper.insertList(upQpointlist);

        // 知识点分析
        List<Map<String, Object>> pointlist = new ArrayList<>();
        if (N_Utils.isListNotEmpty(pointqlist)) {
            LinkedHashMap<String, List<QuestionOrderVo>> pointmap = pointqlist.stream().collect(Collectors.groupingBy(QuestionOrderVo::getId, LinkedHashMap::new,
                                                                                                                      Collectors.toList()));
            // 根据指示进行分组，
            for (Map.Entry<String, List<QuestionOrderVo>> entry : pointmap.entrySet()) {
                List<QuestionOrderVo> pgblist = entry.getValue();
                // 获取知识点的总分
                Double score = pgblist.stream().mapToDouble(QuestionOrderVo::getScore).sum();
                score = N_Utils.formatDouble(score, 1);
                Double srate = N_Utils.getDoubleDivideAndMulitiply(score, paper.getPscore());
                Map<String, Object> prate = new LinkedHashMap<>();
                prate.put("pointid", entry.getKey());
                prate.put("pointname", pgblist.get(0).getName());
                prate.put("score", score);
                prate.put("srate", srate);
                prate.put("ques", pgblist.stream().sorted(Comparator.comparing(QuestionOrderVo::getOrder)).collect(Collectors.toList()));
                pointlist.add(prate);
            }
        }

        MsPaperAnalyze epa = new MsPaperAnalyze();
        epa.setMpid(paper.getMpid());
        epa.setAlljson(JSON.toJSONString(ztmap));// 总体分析
        epa.setQnumjson(JSON.toJSONString(typelist));// 试题栏题型分析
        epa.setComplexityjson(JSON.toJSONString(clist));// 难易度分析
        epa.setPointjson(JSON.toJSONString(pointlist));// 知识点分析
        epa.setQuespointjson(JSON.toJSONString(quesplist));

        // 判断试卷你是否有分析，如果没有直接保存
        MsPaperAnalyze existEpa = msPaperAnalyzeMapper.getObjByMpId(paper.getMpid());
        if (existEpa == null || !N_Utils.isTrueInteger(existEpa.getMpaid())) {
            msPaperAnalyzeMapper.insertUseGeneratedKeys(epa);
        } else {
            epa.setMpaid(existEpa.getMpaid());
            msPaperAnalyzeMapper.updateByPrimaryKey(epa);
        }
    }

    // 设置知识点
    private void setPaperQuestionPointScore(List<QuestionOrderVo> pointqlist, List<QuestionPointVo> quesplist, List<Map<String, Object>> qpoints, MsPaperQtypeQuestionVo dq,
                                            String[] qnstr,String[] qnstrStr, List<Integer> mptqids) {
        if (N_Utils.isListNotEmpty(qpoints)) {
            if (qpoints.size() == 1) {
                // 试题只有一个知识点
                Map<String, Object> pointmap = qpoints.get(0);
                QuestionOrderVo qpoint = new QuestionOrderVo();
                qpoint.setId(pointmap.get("pointid").toString());
                qpoint.setName(pointmap.get("pointname").toString());
                qpoint.setOrder(dq.getQorder());
                qpoint.setScore(dq.getQscore());
                qpoint.setQlevel(dq.getQlevel());
                qpoint.setQuestionid(dq.getQuestionid());
                if (qnstr == null) {
                    qpoint.setQns(new String[]{dq.getQn()});
                    qpoint.setQnstrs(new String[]{dq.getQnstr()});
                } else {
                    qpoint.setQns(qnstr);
                    qpoint.setQnstrs(qnstrStr);
                }

                if (N_Utils.isListEmpty(mptqids)) {
                    qpoint.setMptqids(new Integer[]{dq.getMptqid()});
                } else {
                    Integer[] mptqidstr = mptqids.toArray(new Integer[0]);
                    qpoint.setMptqids(mptqidstr);
                }
                pointqlist.add(qpoint);

                // 试题对应知识点
                QuestionPointVo questionPointVo = new QuestionPointVo();
                questionPointVo.setOrder(dq.getQorder());
                questionPointVo.setScore(dq.getQscore());
                questionPointVo.setQlevel(dq.getQlevel());
                questionPointVo.setQuestionid(dq.getQuestionid());
                List<Map<String, Object>> pointids = new ArrayList<>();
                Map<String, Object> map = new HashMap<>();
                map.put("pointid", pointmap.get("pointid").toString());
                map.put("score", dq.getQscore());
                pointids.add(map);
                questionPointVo.setPointids(pointids);

                if (N_Utils.isListEmpty(mptqids)) {
                    List<Integer> saveids = new ArrayList<>();
                    saveids.add(dq.getMptqid());
                    questionPointVo.setMptqids(saveids);
                    questionPointVo.setMptqid(dq.getMptqid());
                } else {
                    questionPointVo.setMptqids(mptqids);
                    questionPointVo.setMptqid(0);
                }
                quesplist.add(questionPointVo);
            } else {

                // 试题有多个知识点
                // 计算每个知识点所占分值（平均分配）
                Double[] avgps = N_Utils.getPointAvgScore(qpoints.size(), dq.getQscore());
                List<Map<String, Object>> pointids = new ArrayList<>();
                for (int m = 0; m < qpoints.size(); m++) {
                    Map<String, Object> pointmap = qpoints.get(m);
                    QuestionOrderVo qpoint = new QuestionOrderVo();
                    qpoint.setId(pointmap.get("pointid").toString());
                    qpoint.setName(pointmap.get("pointname").toString());
                    qpoint.setOrder(dq.getQorder());
                    qpoint.setQlevel(dq.getQlevel());
                    qpoint.setQuestionid(dq.getQuestionid());


                    Map<String, Object> quesmap = new HashMap<>();// 试题对应知识点
                    quesmap.put("pointid", pointmap.get("pointid").toString());

                    if (avgps.length == 2 && (m + 1) == qpoints.size()) {
                        // 不能整除分，并且是最后一个知识点
                        qpoint.setScore(avgps[1]);
                        quesmap.put("score", avgps[1]);
                    } else {
                        qpoint.setScore(avgps[0]);
                        quesmap.put("score", avgps[0]);
                    }
                    pointids.add(quesmap);

                    // 题号集合
                    if (qnstr == null) {
                        qpoint.setQns(new String[]{dq.getQn()});
                        qpoint.setQnstrs(new String[]{dq.getQnstr()});
                    } else {
                        qpoint.setQns(qnstrStr);
                    }
                    // 试卷中试题id集合
                    if (N_Utils.isListEmpty(mptqids)) {
                        qpoint.setMptqids(new Integer[]{dq.getMptqid()});
                    } else {
                        Integer[] eptqidstr = mptqids.toArray(new Integer[0]);
                        qpoint.setMptqids(eptqidstr);
                    }
                    pointqlist.add(qpoint);
                }

                // 试题对应知识点
                QuestionPointVo questionPointVo = new QuestionPointVo();
                questionPointVo.setOrder(dq.getQorder());
                questionPointVo.setScore(dq.getQscore());
                questionPointVo.setQlevel(dq.getQlevel());
                questionPointVo.setQuestionid(dq.getQuestionid());
                questionPointVo.setPointids(pointids);
                if (N_Utils.isListEmpty(mptqids)) {
                    List<Integer> saveids = new ArrayList<>();
                    saveids.add(dq.getMptqid());
                    questionPointVo.setMptqids(saveids);
                    questionPointVo.setMptqid(dq.getMptqid());

                } else {
                    questionPointVo.setMptqids(mptqids);
                    questionPointVo.setMptqid(0);
                }
                quesplist.add(questionPointVo);

            }

        } else {
            QuestionPointVo questionPointVo = new QuestionPointVo();
            questionPointVo.setOrder(dq.getQorder());
            questionPointVo.setScore(dq.getQscore());
            questionPointVo.setQlevel(dq.getQlevel());
            questionPointVo.setQuestionid(dq.getQuestionid());
            questionPointVo.setPointids(null);
            if (N_Utils.isListEmpty(mptqids)) {
                List<Integer> saveids = new ArrayList<>();
                saveids.add(dq.getMptqid());
                questionPointVo.setMptqids(saveids);
                questionPointVo.setMptqid(dq.getMptqid());
            } else {
                questionPointVo.setMptqids(mptqids);
                questionPointVo.setMptqid(0);
            }

            quesplist.add(questionPointVo);
        }
    }

    // 设置知识点--试卷试题知识点关联关系
    private void setPaperQuestionPointRelation(List<Map<String, Object>> qpoints, MsPaperQtypeQuestionVo dq, List<Integer> mptqids, List<MsPaperQtypeQuestionPoint> upQpointlist, Integer mpid) {
        if (N_Utils.isListNotEmpty(qpoints)) {
            // 试题对应知识点关系
            int i = 0;
            for (Map<String, Object> pointmap : qpoints) {
                String pointid = pointmap.get("pointid").toString();
                String pointname = pointmap.get("pointname").toString();

                if (N_Utils.isListEmpty(mptqids)) {
                    MsPaperQtypeQuestionPoint upPoint = new MsPaperQtypeQuestionPoint();
                    upPoint.setMpid(mpid);
                    upPoint.setMptqid(dq.getMptqid());
                    upPoint.setPointid(pointid);
                    upPoint.setPointname(pointname);
                    upPoint.setMporder(i++);

                    upQpointlist.add(upPoint);
                } else {
                    for (Integer mptqid : mptqids) {
                        MsPaperQtypeQuestionPoint upPoint = new MsPaperQtypeQuestionPoint();
                        upPoint.setMpid(mpid);
                        upPoint.setMptqid(mptqid);
                        upPoint.setPointid(pointid);
                        upPoint.setPointname(pointname);
                        upPoint.setMporder(i++);

                        upQpointlist.add(upPoint);
                    }
                }
            }
        }

    }

    // 设置题型下试题题号及分值
    private void setPaperQuestionQtypeScore(List<QuestionOrderVo> qtypelist, MsPaperQtypeQuestionVo dq, String[] qnstr, Integer[] mptqidstr) {
        QuestionOrderVo qtype = new QuestionOrderVo();
        qtype.setId(dq.getQtypeid());
        qtype.setName(dq.getQtypename());
        qtype.setComplexity(dq.getComplexity());
        qtype.setOrder(dq.getQorder());
        qtype.setScore(dq.getQscore());
        qtype.setQlevel(dq.getQlevel());
        qtype.setQuestionid(dq.getQuestionid());
        if (qnstr == null) {
            qtype.setQns(new String[]{dq.getQn()});
        } else {
            qtype.setQns(qnstr);
        }
        if (mptqidstr == null) {
            qtype.setMptqids(new Integer[]{dq.getMptqid()});
        } else {
            qtype.setMptqids(mptqidstr);
        }

        qtypelist.add(qtype);
    }

    // 设置试题难易度
    private void setPaperQuestionComplexityScore(List<QuestionOrderVo> complexityList, MsPaperQtypeQuestionVo dq, String[] qnstr, Integer[] mptqidstr,
                            List<MsPaperQtypeQuestion> upComplexitylist) {
        QuestionOrderVo qtype = new QuestionOrderVo();
        qtype.setId(dq.getComplexity().toString());// 存放试题难易度
        qtype.setOrder(dq.getQorder());
        qtype.setScore(dq.getQscore());
        qtype.setQlevel(dq.getQlevel());
        qtype.setQuestionid(dq.getQuestionid());
        if (qnstr == null) {
            qtype.setQns(new String[]{dq.getQn()});
        } else {
            qtype.setQns(qnstr);
        }

        if (mptqidstr == null) {
            qtype.setMptqids(new Integer[]{dq.getMptqid()});
        } else {
            qtype.setMptqids(mptqidstr);
        }

        complexityList.add(qtype);
        // 设置试题难易度
        if (mptqidstr == null) {
            MsPaperQtypeQuestion upComplexity = new MsPaperQtypeQuestion();
            upComplexity.setMptqid(dq.getMptqid());
            upComplexity.setComplexity(dq.getComplexity());

            upComplexitylist.add(upComplexity);
        } else {
            for (Integer mptqid : mptqidstr) {
                MsPaperQtypeQuestion upComplexity = new MsPaperQtypeQuestion();
                upComplexity.setMptqid(mptqid);
                upComplexity.setComplexity(dq.getComplexity());

                upComplexitylist.add(upComplexity);
            }
        }


    }

    // 保存试卷分析--附件
    public void savePaperAnalyzeForFj(MsPaper paper) {
        List<MsPaperQtypeVo> fjtypelist = msPaperQtypeMapper.listPaperQtypeQuesitonsForFj(paper.getMpid());
        List<MsPaperQtypeQuestionVo> queslist = new ArrayList<>();
        for (MsPaperQtypeVo fj : fjtypelist) {
            List<MsPaperQtypeQuestionVo> qlist = fj.getQuestions();
            queslist.addAll(qlist);
        }

        List<QuestionOrderVo> pointqlist = new ArrayList<>();// 用于存放知识点，以及知识点下得分
        List<QuestionPointVo> quesplist = new ArrayList<>();// 单题对应知识点

        // 总体分析（主观题、客观题）
        // 处理题型1单选题2多选题3主观题4判断对错5判断√×6判断TF11综合题12听力13填空题
        int znum = 0;
        double zscore = 0;
        int knum = 0;
        double kscore = 0;
        for (MsPaperQtypeQuestionVo q : queslist) {
            if (N_Utils.isObjectiveQuestion(q.getCtype())) {
                knum++;
                kscore = kscore + q.getQscore();
            } else {
                znum++;
                zscore = zscore + q.getQscore();
            }

            List<Map<String, Object>> qpoints = q.getPoints();
            if (qpoints != null) {
                // 存放知识点
                setPaperQuestionPointScore(pointqlist, quesplist, qpoints, q, null, null,null);
            }
        }

        double znumrate = N_Utils.getIntegerDivideAndMulitiply(znum, paper.getPnum());
        double knumrate = N_Utils.getDoubleReduce(100.0, znumrate);

        double zscorerate = N_Utils.getDoubleDivideAndMulitiply(zscore, paper.getPscore());
        double kscorerate = N_Utils.getDoubleReduce(100.0, zscorerate);

        List<Map<String, Object>> ranglist = new ArrayList<>();
        Map<String, Object> zgmap = new TreeMap<>();
        zgmap.put("qtname", "主观题");
        zgmap.put("score", zscore);
        zgmap.put("num", znum);
        zgmap.put("srate", zscorerate);
        zgmap.put("nrate", znumrate);
        ranglist.add(zgmap);
        Map<String, Object> kgmap = new TreeMap<>();
        kgmap.put("qtname", "客观题");
        kgmap.put("score", kscore);
        kgmap.put("num", knum);
        kgmap.put("srate", kscorerate);
        kgmap.put("nrate", knumrate);
        ranglist.add(kgmap);

        Map<String, Object> ztmap = new TreeMap<>();
        ztmap.put("pnum", paper.getPnum());
        ztmap.put("pscore", paper.getPscore());
        ztmap.put("ranglist", ranglist);

        // 题型分布(按照名称进行分组)
        fjtypelist.sort(Comparator.comparing(MsPaperQtypeVo::getMptorder));
        Map<String, List<MsPaperQtypeVo>> qtypemap = fjtypelist.stream().collect(Collectors.groupingBy(MsPaperQtypeVo::getMptname, Collectors.toList()));
        List<Map<String, Object>> qtlist = new ArrayList<>();
        for (Map.Entry<String, List<MsPaperQtypeVo>> entry : qtypemap.entrySet()) {
            List<MsPaperQtypeVo> aq = entry.getValue();
            int num = aq.stream().mapToInt(MsPaperQtypeVo::getMptnum).sum();
            double tscore = aq.stream().mapToDouble(MsPaperQtypeVo::getMptscore).sum();
            tscore = N_Utils.formatDouble(tscore, 1);
            double storerate = N_Utils.getDoubleDivideAndMulitiply(tscore, paper.getPscore());
            // 获取小题题号

            List<Integer> orderlist = new ArrayList<>();
            List<Integer> mptqidlist = new ArrayList<>();
            List<String> qnlist = new ArrayList<>();
            List<Double> scorelist = new ArrayList<>();
            List<String> qnamelist = new ArrayList<>();
            for (MsPaperQtypeVo t : aq) {
                List<MsPaperQtypeQuestionVo> qlist = t.getQuestions();
                for (MsPaperQtypeQuestionVo q : qlist) {
                    orderlist.add(q.getQorder());
                    mptqidlist.add(q.getMptqid());
                    qnlist.add(q.getQn());
                    scorelist.add(q.getQscore());
                    qnamelist.add(q.getQtypename());
                }
            }

            Map<String, Object> anmap = new TreeMap<>();// 题型对应试题的id和基础信息
            anmap.put("orders", orderlist);
            anmap.put("mptqids", mptqidlist);
            anmap.put("qns", qnlist);
            anmap.put("scores", scorelist);
            anmap.put("qtypenames", qnamelist);

            Map<String, Object> tmap = new TreeMap<>();
            tmap.put("qtname", entry.getKey());
            tmap.put("qtid", aq.get(0).getMptid());
            tmap.put("num", num);
            tmap.put("score", tscore);
            tmap.put("srate", storerate);
            tmap.put("ques", anmap);
            qtlist.add(tmap);
        }

        // 试卷中试题难易度
        String complexityJson = null;
        List<MsPaperQtypeQuestionVo> hasComplexitys = queslist.stream().filter(q -> N_Utils.isTrueInteger(q.getComplexity())).collect(Collectors.toList());
        if (!hasComplexitys.isEmpty()) {
            Map<Integer, List<MsPaperQtypeQuestionVo>> complexmap = queslist.stream().collect(Collectors.groupingBy(MsPaperQtypeQuestionVo::getComplexity, Collectors.toList()));
            List<Map<String, Object>> clist = new ArrayList<>();
            for (Map.Entry<Integer, List<MsPaperQtypeQuestionVo>> entry : complexmap.entrySet()) {
                List<MsPaperQtypeQuestionVo> pgblist = entry.getValue();
                // 处理需要保存的ques集合
                List<Map<String, Object>> quesList = new ArrayList<>();
                for (MsPaperQtypeQuestionVo q : pgblist) {
                    Map<String, Object> qmap = new TreeMap<>();
                    qmap.put("id", entry.getKey());
                    qmap.put("mptqid", q.getMptqid());
                    qmap.put("order", q.getQorder());
                    qmap.put("qlevel", 1);
                    qmap.put("qns", q.getQn());
                    qmap.put("score", q.getQscore());

                    quesList.add(qmap);
                }

                Double score = pgblist.stream().mapToDouble(MsPaperQtypeQuestionVo::getQscore).sum();
                score = N_Utils.formatDouble(score, 1);
                Double srate = N_Utils.getDoubleDivideAndMulitiply(score, paper.getPscore());
                Map<String, Object> prate = new TreeMap<>();
                prate.put("level", entry.getKey());
                prate.put("score", score);
                prate.put("srate", srate);
                prate.put("ques", quesList);
                clist.add(prate);
            }
            complexityJson = JSON.toJSONString(clist);
        }

        // 试卷中试题知识点
        String pointJson = null;
        String quesPointJson = null;
        if (N_Utils.isListNotEmpty(pointqlist)) {
            List<Map<String, Object>> pointlist = new ArrayList<>();
            LinkedHashMap<String, List<QuestionOrderVo>> pointmap = pointqlist.stream().collect(Collectors.groupingBy(QuestionOrderVo::getId, LinkedHashMap::new, Collectors.toList()));
            // 根据指示进行分组，
            for (Map.Entry<String, List<QuestionOrderVo>> entry : pointmap.entrySet()) {
                List<QuestionOrderVo> pgblist = entry.getValue();
                // 获取知识点的总分
                Double score = pgblist.stream().mapToDouble(QuestionOrderVo::getScore).sum();
                score = N_Utils.formatDouble(score, 1);
                Double srate = N_Utils.getDoubleDivideAndMulitiply(score, paper.getPscore());
                Map<String, Object> prate = new LinkedHashMap<>();
                prate.put("pointid", entry.getKey());
                prate.put("pointname", pgblist.get(0).getName());
                prate.put("score", score);
                prate.put("srate", srate);
                prate.put("ques", pgblist.stream().sorted(Comparator.comparing(QuestionOrderVo::getOrder)).collect(Collectors.toList()));
                pointlist.add(prate);
            }

            pointJson = JSON.toJSONString(pointlist);
            quesPointJson = JSON.toJSONString(quesplist);
        }

        MsPaperAnalyze epa = new MsPaperAnalyze();
        epa.setMpid(paper.getMpid());
        epa.setAlljson(JSON.toJSONString(ztmap));
        epa.setQnumjson(JSON.toJSONString(qtlist));
        epa.setComplexityjson(complexityJson);
        epa.setPointjson(pointJson);
        epa.setQuespointjson(quesPointJson);

        // 判断试卷你是否有分析，如果没有直接保存
        MsPaperAnalyze existEpa = msPaperAnalyzeMapper.getObjByMpId(paper.getMpid());
        if (existEpa == null || !N_Utils.isTrueInteger(existEpa.getMpaid())) {
            msPaperAnalyzeMapper.insertUseGeneratedKeys(epa);
        } else {
            epa.setMpaid(existEpa.getMpaid());
            msPaperAnalyzeMapper.updateByPrimaryKey(epa);
        }
    }

}


