4614: 【GESP2403五级】成绩排序

内存限制:128 MB 时间限制:1.000 S
评测方式:文本比较 命题人:
提交:4 解决:4

题目描述


输入

第一行一个整数$N$ ,表示同学的人数。
接下来$N$ 行,每行三个非负整数$c_i$,$m_i$,$e_i$ 分别表示该名同学的语文、数学、英语成绩。
保证$0\le c_i,m_i,e_i\le 150$ 。

输出

输出$N$ 行,按输入同学的顺序,输出他们的排名。
注意:请不要按排名输出同学的序号,而是按同学的顺序输出他们各自的排名

样例输入 复制

6
140 140 150
140 149 140
148 141 140
141 148 140
145 145 139
0 0 0

样例输出 复制

1
3
4
4
2
6

提示

#include <iostream>
#include <algorithm>  // 使用 sort

using namespace std;

struct Student {
    int id;          // 原始输入顺序
    int ch, math, eng;
    int total;       // 总分
    int cm_total;    // 语文+数学总分
    int cm_max;      // 语文和数学的最高分
};

// 比较函数
bool compare(const Student& a, const Student& b) {
    if (a.total != b.total) return a.total > b.total;
    if (a.cm_total != b.cm_total) return a.cm_total > b.cm_total;
    if (a.cm_max != b.cm_max) return a.cm_max > b.cm_max;
    return false;  // 完全相等时,顺序任意
}

int main() {
    int N;
    cin >> N;

    // 使用原生数组(静态分配,N ≤ 10000 栈上够用)
    // 如果担心栈溢出,可以改为静态数组或堆分配
    Student students[10000];  // 最大 N=10000
    int ranks[10000];

    // 读入数据
    for (int i = 0; i < N; ++i) {
        students[i].id = i;
        cin >> students[i].ch >> students[i].math >> students[i].eng;
        students[i].total = students[i].ch + students[i].math + students[i].eng;
        students[i].cm_total = students[i].ch + students[i].math;

        // 计算语文和数学的最高分(不用 max 函数)
        if (students[i].ch > students[i].math) {
            students[i].cm_max = students[i].ch;
        } else {
            students[i].cm_max = students[i].math;
        }
    }

    // 使用 sort 排序(只用了 algorithm,没用 vector)
    sort(students, students + N, compare);

    // 计算排名
    int rank = 1;
    for (int i = 0; i < N; ++i) {
        if (i > 0) {
            Student& prev = students[i - 1];
            Student& curr = students[i];
            // 判断是否与前一名并列
            if (prev.total == curr.total &&
                prev.cm_total == curr.cm_total &&
                prev.cm_max == curr.cm_max) {
                // 并列,排名相同
                ranks[curr.id] = ranks[prev.id];
            } else {
                rank = i + 1;
                ranks[curr.id] = rank;
            }
        } else {
            ranks[students[i].id] = rank;
        }
    }

    // 按输入顺序输出排名
    for (int i = 0; i < N; ++i) {
        cout << ranks[i] << endl;
    }

    return 0;
}


#include <iostream>
#include <algorithm>
#include <tuple>
using namespace std;
const int MAX_N = 10005;
tuple < int, int, int, int > students[MAX_N];
int main() {
    ios::sync_with_stdio(false);
    int N;
    cin >> N;
    for (int i = 0; i < N; ++i) {
        int c, m, e;
        cin >> c >> m >> e;
        students[i] = make_tuple(c + m + e, c + m, max(c, m), i);
    }
    sort(students, students + N, greater < tuple < int, int, int, int >> ());
    int rank[N];
    int curr_rank;
    tuple < int, int, int > last_student = make_tuple(-1, -1, -1);
    for (int i = 0; i < N; ++i) {
        if (make_tuple(get < 0 > (students[i]), get < 1 > (students[i]), get < 2 >
                (students[i])) != last_student) {
            last_student = make_tuple(get < 0 > (students[i]), get < 1 > (students[i]),
                get < 2 > (students[i]));
            curr_rank = i + 1;
        }
        rank[get < 3 > (students[i])] = curr_rank;
    }
    for (int i = 0; i < N; ++i) {
        cout << rank[i] << endl;
    }
    return 0;
}