Greasy Fork

Greasy Fork is available in English.

HEU成绩助手

简单的统计和计算成绩,输出到控制台

您需要先安装一个扩展,例如 篡改猴Greasemonkey暴力猴,之后才能安装此脚本。

You will need to install an extension such as Tampermonkey to install this script.

您需要先安装一个扩展,例如 篡改猴暴力猴,之后才能安装此脚本。

您需要先安装一个扩展,例如 篡改猴Userscripts ,之后才能安装此脚本。

您需要先安装一款用户脚本管理器扩展,例如 Tampermonkey,才能安装此脚本。

您需要先安装用户脚本管理器扩展后才能安装此脚本。

(我已经安装了用户脚本管理器,让我安装!)

您需要先安装一款用户样式管理器扩展,比如 Stylus,才能安装此样式。

您需要先安装一款用户样式管理器扩展,比如 Stylus,才能安装此样式。

您需要先安装一款用户样式管理器扩展,比如 Stylus,才能安装此样式。

您需要先安装一款用户样式管理器扩展后才能安装此样式。

您需要先安装一款用户样式管理器扩展后才能安装此样式。

您需要先安装一款用户样式管理器扩展后才能安装此样式。

(我已经安装了用户样式管理器,让我安装!)

// ==UserScript==
// @name         HEU成绩助手
// @namespace    http://tampermonkey.net/
// @version      0.1
// @description  简单的统计和计算成绩,输出到控制台
// @author       HC
// @match        http://edusys.hrbeu.edu.cn/jsxsd/kscj/cjcx_list
// @grant        none
// ==/UserScript==

// 解析表格
const table = [];
for (let tr of document.querySelector('#dataList > tbody').children) {
    const row = [];
    for (const th of tr.children) {
        row.push(th.innerText);
    }
    table.push(row);
}
const title = table[0]; // 表格的第一行,标题内容
const course = table.slice(1);  // 截取课程内容

function findTitle(name) {
    for (let i = 0; i < title.length; i++) {
        if (title[i] === name) return i;
    }
    console.error('未找到' + name + ',解析失败!');
    return -1;
}

// 表格数据加工
(function () {
    // 将评级转化为分数
    let index1 = findTitle('成绩');
    if (index1 === -1) return 0;
    for (let tr of course) {
        switch (tr[index1]) {
            case '优秀':
                tr[index1] = 95;
                break;
            case '良好':
                tr[index1] = 85;
                break;
            case '中等':
                tr[index1] = 75;
                break;
            case '及格':
                tr[index1] = 65;
                break;
            case '不及格':
                tr[index1] = 30;
                break;
            default:
                tr[index1] = parseInt(tr[index1]);
                if (isNaN(tr[index1])) {
                    tr[index1] = 0; // 无法转化成数字的,就当做0处理
                }
        }
    }

    // 剔除重复内容(补考/刷分,取最高分);
    let index2 = findTitle('课程编号');
    if (index2 === -1) return 0;
    course.sort((a, b) => a[index2] - b[index2]); // 按课程编号从小到大排序
    for (let i = 1; i < course.length; i++) {
        if (course[i - 1][index2] === course[i][index2]) {
            console.log("检测到重复课程数据,将自动保留最高分,剔除低分数据:", course[i - 1], course[i]);
            if (course[i - 1][index1] < course[i][index1]) {
                course.splice(i - 1, 1);
            } else course.splice(i, 1);
            i--;
        }
    }

    // 将学分转化为数字
    index1 = findTitle('学分');
    if (index1 === -1) return 0;
    for (const tr of course) {
        tr[index1] = parseFloat(tr[index1]);
    }
})();

// 课程分类与整理
const mustCourse = [];  // 必修
const publicCourse = [];// 公选
const otherCourse = []; // 其他
(function () {
    let index1 = findTitle('课程名称');
    let index2 = findTitle('成绩');
    let index3 = findTitle('学分');
    let index4 = findTitle('课程属性');
    let index5 = findTitle('课程性质');
    let index6 = findTitle('通识教育选修课程类别');
    if (index1 === -1 || index2 === -1 || index3 === -1 || index4 === -1 || index5 === -1 || index6 === -1) return 0;

    for (let tr of course) {
        if (tr[index4] === '必修') {
            mustCourse.push([tr[index1], tr[index2], tr[index3], tr[index5]]);
        } else if (tr[index4] === '公选') {
            publicCourse.push([tr[index1], tr[index2], tr[index3], tr[index5], tr[index6]])
        } else {    // 其它
            otherCourse.push([tr[index1], tr[index2], tr[index3], tr[index5]]);
        }
    }
    console.log('必修课程:', mustCourse);
    console.log('公选课程:', publicCourse);
    console.log('其它课程:', otherCourse);
})();

// 成绩计算与统计
(function () {
    // 统计必修课成绩
    const must = [0, 0];
    for (let tr of mustCourse) {
        must[0] += tr[1] * tr[2];
        must[1] += tr[2];
    }
    console.log('必修课成绩:', '加权平均分:' + must[0] / must[1], '总学分:' + must[1]);

    // 统计公选课程
    const publicC = [0, 0];
    for (let tr of publicCourse) {
        publicC[0] += tr[1] * tr[2];
        publicC[1] += tr[2];
    }
    console.log('公选课成绩:', '加权平均分:' + publicC[0] / publicC[1], '总学分:' + publicC[1]);

    // 统计其它专选课
    const other = [0, 0];
    for (let tr of otherCourse) {
        other[0] += tr[1] * tr[2];
        other[1] += tr[2];
    }
    console.log('其它课成绩:', '加权平均分:' + other[0] / other[1], '总学分:' + other[1]);

    console.log('公选课加上其它课成绩:', '加权平均分:' + (must[0] + other[0]) / (must[1] + other[1]), '总学分:' + (must[1] + other[1]));
})()