由浙江大学计算机科学与技术学院主办。每个测试应该在多个地方同时运行,并且排名列表将在测试后立即合并。现在你的工作是编写一个程序来正确合并所有排名列表并生成最终排名。
每个输入文件包含一个测试用例。对于每种情况,第一行包含一个正数 N (≤100),即测试位置的数量。然后是 N 个排名表,每行开头包含正整数 K(≤300)、考生人数,然后 K 行包含报名号(13 位数字)和每个考生的总成绩。一行中的所有数字均以空格分隔。
对于每个测试用例,首先在一行中打印测试者的总数。然后按以下格式打印最终排名表:
registration_number final_rank location_number local_rank
位置从 1 到 N 编号。输出必须按最终排名的非降序排序。相同分数的考生必须具有相同的排名,并且输出必须按照其注册编号的非降序排列。
2
5
1234567890001 95
1234567890005 100
1234567890003 95
1234567890002 77
1234567890004 85
4
1234567890013 65
1234567890011 25
1234567890014 100
1234567890012 85
9
1234567890005 1 1 1
1234567890014 1 2 1
1234567890001 3 1 2
1234567890003 3 1 2
1234567890004 5 1 4
1234567890012 5 2 2
1234567890002 7 1 5
1234567890013 8 2 3
1234567890011 9 2 4
#include <iostream>
#include <cstring>
#include <algorithm>
#include <limits>
#include <vector>
#include <cstdio>
struct Student
{
char id[14];
int score;
int r;
int location = -1;
int rl;
};
bool cmp(Student a, Student b)
{
if (a.score != b.score)
return a.score > b.score;
else
return strcmp(a.id, b.id) < 0;
}
int main()
{
using namespace std;
int locations = 0;
int number = 0;
int n = 0;
char registration_number[14];
vector<Student> sumstudents;
freopen("input.txt", "r", stdin);
fscanf(stdin, "%d", &locations); //fscanf返回值需检查
for (int i = 1; i <= locations; i++)
{
vector<Student> students;
fscanf(stdin, "%d", &n);
for (int j = 0; j < n; j++)
{
fscanf(stdin, "%13s%d", registration_number, &number);
if (strlen(registration_number) > 13)
{
cerr << "准考证号只有十三位" << endl;
return 1;
}
Student student;
size_t idlength = strlen(registration_number);
if (sizeof(student.id) >= idlength + 1)
copy_n(registration_number, idlength, student.id);
else
cout << "数组长度设置有问题";
student.score = number;
student.r = 0;
student.rl = 0;
student.location = i;
students.push_back(student);
registration_number[0] = '\0';
}
std::sort(students.begin(), students.end(), cmp);
students[0].rl = 1;
sumstudents.push_back(students[0]);
for (size_t i = 1; i < students.size(); i++)
{
if (students[i].score == students[i - 1].score)
{
students[i].rl = students[i - 1].rl;
}
else
{
students[i].rl = i + 1;
}
sumstudents.push_back(students[i]);
}
students.clear();
// auto it = find_if(students.begin(), students.end(), [&](const Student &s)
// { return s.location == i; });
// if (it->location != -1)
// it->rl = 1;
// int flag = 1;
// while (it != students.end())
// {
// flag++;
// auto pre = it;
// it = std::find_if(++it, students.end(), [&](const Student &s)
// { return s.location == i; });
// if (it->score == pre->score)
// it->rl = pre->rl;
// else
// it->rl = flag;
// }
}
std::sort(sumstudents.begin(), sumstudents.end(), cmp);
sumstudents[0].r = 1;
for (size_t i = 1; i < sumstudents.size(); i++)
{
if (sumstudents[i].score == sumstudents[i - 1].score)
sumstudents[i].r = sumstudents[i - 1].r;
else
sumstudents[i].r = i + 1;
}
cout << sumstudents.size();
for (Student student : sumstudents)
{
cout << '\n'<< student.id << ' ' << student.r << ' ' << student.location << ' ' << student.rl;
}
sumstudents.clear();
return 0;
}
#include <iostream>
#include <cstdio>
#include <vector>
#include <algorithm>
using namespace std;
struct Person
{
// sco: score, fr: final rank
// ln: location number, lr: local rank
string id;
int sco, fr, ln, lr;
};
// compare by score
bool CompSco(Person p1, Person p2)
{
if (p1.sco == p2.sco)
{
return p1.id < p2.id;
}
else
{
return p1.sco > p2.sco;
}
}
int main()
{
#ifdef ONLINE_JUDGE
#else
freopen("input.txt", "r", stdin);
#endif // ONLINE_JUDGE
int N, K, total = 0;
if (scanf("%d", &N) != 1)
{
// 错误处理,例如:打印错误消息,退出程序
cerr << "Error reading N from input." << endl;
return 1; // 或者 exit(EXIT_FAILURE);
}
vector<Person> pers;
Person per;
char id[14];
// input
for (int i = 1; i <= N; i++)
{
if (scanf("%d", &K) != 1)
{
cerr << "Error reading K from input." << endl;
return 1; // 或者 exit(EXIT_FAILURE);
}
vector<Person> tmps; // ** call tmps for simplifying
for (int j = 0; j < K; j++)
{
if (scanf("%s %d", id, &per.sco) != 2)
{
cerr << "Error reading ID and/or score from input." << endl;
return 1; // 或者 exit(EXIT_FAILURE);
}
per.id = id;
per.ln = i;
per.fr = per.lr = -1;
tmps.push_back(per);
}
// sort local rank
sort(tmps.begin(), tmps.end(), CompSco);
tmps[0].lr = 1; //** especially handle zero
pers.push_back(tmps[0]);
for (int j = 1; j < K; j++)
{
if (tmps[j].sco == tmps[j - 1].sco)
{
tmps[j].lr = tmps[j - 1].lr;
}
else
{
tmps[j].lr = j + 1;
}
pers.push_back(tmps[j]);
}
total += K;
}
// sort final rank
sort(pers.begin(), pers.end(), CompSco);
pers[0].fr = 1; // especially handle zero
for (int k = 1; k < total; k++)
{
if (pers[k].sco == pers[k - 1].sco)
{
pers[k].fr = pers[k - 1].fr;
}
else
{
pers[k].fr = k + 1;
}
}
// output
printf("%d", total);
for (auto p : pers)
{
printf("\n%s %d %d %d", p.id.c_str(), p.fr, p.ln, p.lr);
}
return 0;
}
我想知道为什么我的代码是错误的,而另一个是正确的,看起来没有区别
#include <iostream>
#include <cstring>
#include <algorithm>
#include <limits>
#include <vector>
struct Student
{
char id[14];
int score;
int r;
int location = -1;
int rl;
};
bool cmp(Student a, Student b)
{
if (a.score != b.score)
return a.score > b.score;
else
return strcmp(a.id, b.id) < 0;
}
int main()
{
using namespace std;
int locations = 0;
int number = 0;
int n = 0;
char registration_number[14];
vector<Student> allstudents;
cin >> locations;
for (int i = 1; i <= locations; i++)
{
vector<Student> students;
cin >> n;
cin.get();
for (int j = 0; j < n; j++)
{
cin.getline(registration_number, 14, ' ');
if (cin.fail())
{
cerr << "The admission ticket number is only thirteen" << endl;
return 1;
}
if (!(cin >> number))
{
cerr << "Error reading the integer." << endl;
return 1;
}
cin.ignore(numeric_limits<std::streamsize>::max(), '\n');
Student student;
size_t idlength = strlen(registration_number);
if (sizeof(student.id) >= idlength + 1)
strncpy(student.id, registration_number, 14);
else
cout << "There is a problem with the array length setting";
student.score = number;
student.r = 0;
student.rl = 0;
student.location = i;
students.push_back(student);
}
if (students.size() > 0)
{
// The time complexity is greatly increased: sort and find_if
// std::sort(students.begin(), students.end(), cmp);
// auto it = find_if(students.begin(), students.end(), [&](const Student &s)
// { return s.location == i; });
// if (it->location != -1)
// it->rl = 1;
// int flag = 1;
// while (it != students.end())
// {
// flag++;
// auto pre = it;
// it = std::find_if(++it, students.end(), [&](const Student &s)
// { return s.location == i; });
// if (it->score == pre->score)
// it->rl = pre->rl;
// else
// it->rl = flag;
// }
sort(students.begin(), students.end(), cmp);
students[0].rl = 1;
allstudents.push_back(students[0]);
for (size_t i = 1; i < students.size(); i++)
{
if (students[i].score == students[i - 1].score)
students[i].rl = students[i - 1].rl;
else
students[i].rl = i + 1;
allstudents.push_back(students[i]);
}
}
students.clear();
}
if (allstudents.size() > 0)
{
sort(allstudents.begin(), allstudents.end(), cmp);
allstudents[0].r = 1;
for (size_t i = 1; i < allstudents.size(); i++)
{
if (allstudents[i].score == allstudents[i - 1].score)
allstudents[i].r = allstudents[i - 1].r;
else
allstudents[i].r = i + 1;
}
cout << allstudents.size();
for (Student student : allstudents)
{
cout << endl
<< student.id << ' ' << student.r << ' ' << student.location << ' ' << student.rl;
}
allstudents.clear();
}
return 0;
}
copy_n函数不会插入空字符。一起使用 std::sort 和 std::find_if 会大大增加时间复杂度。