1
题目大意

有N个考场,每个考场有K个考生。现在给出各个考场中考生的准考证号与分数,要求将所有考生按分数从高到低排序,并按顺序输出所有考生的准考证号、排名、考场号以及考场内排名。

算法思路

这是一道比较常规的排序题目,题目要求获取每一个考场的考生本考场的排名和最终所有考生在一起的最终排名,那么就先使用
vector<Student> students[N+1]来保存每一个考场的考生,然后使用vector<Student> stu保存所有考场的考生集合,首先对于考场i的学生stuents[i]使用sort函数直接进行排序获取排名,然后将获取了本地考场排名的学生添加进stu中,然后再对stu进行排序,获取每一个考生的最终排名,最后按照题目要求进行输入即可。

获取排名的方法

对于排序后第一个考生名次为1,然后对于其余考生若与前一个考生的分数相同获得相同排名,否则等于排在前面的人数加1。

注意点
  1. 考生编号为13位需要使用字符数组或者字符串进行存储。
  2. 这里使用了string类型进行存储,输入的时候先使用字符数组进行输入,然后直接赋值给string类型变量,这样在数据量较高的使用比cin输入要快,输入的时候得使用c_str()函数转化为字符数组进行输出.
提交结果

pat a 1025提交结果

实现代码
#include<cstdio>
#include<vector>
#include<algorithm>
#include<string>

using namespace std;

int N;//考场数目
int K;//每一个考场的人数

struct Student{
    string registration_number;// 考生编号,13位
    int total_score; // 总分
    int location_number; // 考场编号,从1开始
    int local_rank; // 本考场排名
    int final_rank; // 最终排名
};

bool cmp(Student a,Student b){
    if (a.total_score!=b.total_score){
        return a.total_score>b.total_score;
    } else{
        return a.registration_number<b.registration_number;
    }
}

int main(){
    scanf("%d",&N);
    vector<Student> students[N+1]; // 所有考生的集合,studnets[i]就是考场编号为i的考生集合
    vector<Student> stu; // 所有考生集合
    int index = 0;
    char registration_number[15];
    for (int i = 1; i <=N; ++i) {
        scanf("%d",&K);
        for (int j = 0; j < K; ++j) {
            Student student;
            scanf("%s %d",registration_number,&student.total_score);
            student.registration_number = registration_number;
            student.location_number = i;
            students[i].push_back(student);
        }
    }
    // 首先对本考场的学生进行排序获取排名
    for (int i = 1; i <= N; ++i) {
        sort(students[i].begin(),students[i].end(),cmp);
        // 计算排名
        for (int j = 0; j < students[i].size(); ++j) {
            if (j==0){
                students[i][j].local_rank = 1;// 第一个排名为1
            } else if (students[i][j].total_score==students[i][j-1].total_score){
                // 总分一样排名一样
                students[i][j].local_rank = students[i][j-1].local_rank;
            } else{
                // 总分不一样,排名为前面的人数加一
                students[i][j].local_rank = j+1;
            }
            // 计算完本考场排名后加入stu中,获取最终排名
            stu.push_back(students[i][j]);
        }
    }
    // 对所有考生进行排序
    sort(stu.begin(),stu.end(),cmp);
    // 获取考生的总排名
    for (int k = 0; k < stu.size(); ++k) {
        if (k==0){
            stu[k].final_rank = 1;
        } else if (stu[k].total_score==stu[k-1].total_score){
            stu[k].final_rank = stu[k-1].final_rank;
        } else{
            stu[k].final_rank = k+1;
        }
    }
    // 输出所有考生的信息
    printf("%d\n",stu.size());
    for (int l = 0; l < stu.size(); ++l) {
        printf("%s %d %d %d\n",stu[l].registration_number.c_str(),stu[l].final_rank,stu[l].location_number,stu[l].local_rank);
    }
    return 0;
}

乔梓鑫
569 声望17 粉丝

主要分享个人学习经验和心得