CHAPTER_4 算法初步入门
4.1 排序
题目:
有n个考场,每个考场有若干数量的考生。现在给出各个考场中考生的准考证号与分数,要求将考生按分数从高至低排序,并按顺序输出所有考生的准考证号、排名、考场号、考场内排名。(当学生成绩相同时,排名相同)
输入样例:
2
4
1001 95
1002 100
1003 95
1004 77
3
1005 85
1006 94
1007 27
输出样例:
1002 1 1 1
1001 2 1 2
1003 2 1 2
1006 4 2 1
1005 5 2 2
1004 6 1 4
1007 7 2 3
思路:
使用结构体(struct)或者类(class)存放学生的准考证号、分数、考场号、排名、考场内排名。
根据要求,编写排序函数cmp规则如下:
(1)分数不同时,按分数由高到低排序
(2)分数相同时,按准考证号由高到低排序
即如下:
struct student{
int id;
int score;
int local;
int rank;
int l_rank;
};
bool cmp(student a,student b){
if(a.score!=b.score)
return a.score>b.score;
else
a.id>b.id;
}
算法步骤:按样例读入各考场学生信息,每读完一个考场信息后对该考场学生按score排序;读完所有信息后,对所有考生排序;输出所有学生信息
参考代码:
#include<iostream>
#include<algorithm>
using namespace std;
struct student{
int id;
int score;
int local;
int rank;
int l_rank;
}stu[1024];
//存放学生信息
bool cmp(student a,student b){
if(a.score!=b.score)
return a.score>b.score;
else
return a.id>b.id;
}
//排序规则
int main(){
int n,l_num,num=0,l=1; //n为考场数,num为学生总数 ,l_num为考场学生人数 ,l为考场号 (起始为1)
cin>>n;
while(n--){
cin>>l_num;
for(int i=0;i<l_num;i++){
cin>>stu[num].id>>stu[num].score;
stu[num].local=l;
num++;
}
l++; //输入该考场学生考号和成绩,输入完后考场号加1
sort(stu+num-l_num,stu+num,cmp); //对该考场输入 学生按规则排序,该考场学生起始位置stu+num-l_num,共l_num个学生
stu[num-l_num].l_rank=1;
for(int i=num-l_num+1;i<num;i++){
if(stu[i].score==stu[i-1].score)
stu[i].l_rank=stu[i-1].l_rank;
else
stu[i].l_rank=i+l_num-num+1;
} //将该考场第一名学生考场排名置为1。从第二名开始,后续学生成绩如果与前一位相同 ,则考场排名与前一位相同,否则为当前下标+1
}
cout<<num<<endl;
sort(stu,stu+num,cmp); //输出考场总人数,然后对所有考生排序
stu[0].rank=1;
for(int i=1;i<num;i++){
if(stu[i].score==stu[i-1].score)
stu[i].rank=stu[i-1].rank;
else
stu[i].rank=i+1;
} //将第一名学生考场排名置为1。从第二名开始,后续学生成绩如果与前一位相同 ,则总排名与前一位相同,否则为当前下标+1
for(int i=0;i<num;i++){
cout<<stu[i].id<<' '<<stu[i].rank<<' '<<stu[i].local<<' '<<stu[i].l_rank<<endl;
}
return 0;
}