批改多选题是比较麻烦的事情,有很多不同的计分方法。有一种最常见的计分方法是:如果考生选择了部分正确选项,并且没有选择任何错误选项,则得到50%分数;如果考生选择了任何一个错误的选项,则不能得分。本题就请你写个程序帮助老师批改多选题,并且指出哪道题的哪个选项错的人最多。
输入格式:
输入在第一行给出两个正整数N(<=1000)和M(<=100),分别是学生人数和多选题的个数。随后M行,每行顺次给出一道题的满分值(不超过5的正整数)、选项个数(不少于2且不超过5的正整数)、正确选项个数(不超过选项个数的正整数)、所有正确选项。注意每题的选项从小写英文字母a开始顺次排列。各项间以1个空格分隔。最后N行,每行给出一个学生的答题情况,其每题答案格式为“(选中的选项个数 选项1 ……)”,按题目顺序给出。注意:题目保证学生的答题情况是合法的,即不存在选中的选项数超过实际选项数的情况。
输出格式:
按照输入的顺序给出每个学生的得分,每个分数占一行,输出小数点后1位。最后输出错得最多的题目选项的信息,格式为:“错误次数 题目编号(题目按照输入的顺序从1开始编号)-选项号”。如果有并列,则每行一个选项,按题目编号递增顺序输出;再并列则按选项号递增顺序输出。行首尾不得有多余空格。如果所有题目都没有人错,则在最后一行输出“Too simple”。
输入样例1:3 4 3 4 2 a c 2 5 1 b 5 3 2 b c 1 5 4 a b d e (2 a c) (3 b d e) (2 a c) (3 a b e) (2 a c) (1 b) (2 a b) (4 a b d e) (2 b d) (1 e) (1 c) (4 a b c d)输出样例1:
3.5 6.0 2.5 2 2-e 2 3-a 2 3-b输入样例2:
2 2 3 4 2 a c 2 5 1 b (2 a c) (1 b) (2 a c) (1 b)输出样例2:
5.0 5.0Too simple
#include<iostream> #include<string> using namespace std; struct subject { double grade; int num_of_opt; int num_of_right_answer; string choice = ""; int wrong_answer[5] = { 0 }; }; int main() { int n, m; cin >> n >> m; subject sub[100]; string tmp; string(*student_answer)[100]; student_answer = new string[1000][100]; double total[1000] = { 0 }; for (int i = 0; i < m; i++) { cin >> sub[i].grade >> sub[i].num_of_opt >> sub[i].num_of_right_answer; for (int j = 0; j < sub[i].num_of_right_answer; j++) { cin >> tmp; sub[i].choice = sub[i].choice+tmp; } }//以上存储了所有正确答案 getchar(); for (int i = 0; i < n; i++) { getline(cin, tmp); for (int j = 0; j < m; j++) { int t = tmp.find(')'); string s = tmp.substr(0, t); if (s.find('a') != s.npos) student_answer[i][j] = student_answer[i][j]+ "a"; if (s.find('b') != s.npos) student_answer[i][j] = student_answer[i][j]+"b"; if (s.find('c') != s.npos) student_answer[i][j] = student_answer[i][j]+"c"; if (s.find('d') != s.npos) student_answer[i][j] = student_answer[i][j]+ "d"; if (s.find('e') != s.npos) student_answer[i][j] = student_answer[i][j]+ "e"; if(j!=m-1) tmp = tmp.substr(t + 2); } }//以上读取了所有学生的答案 int flag = 1;//没人错的标记 for (int i = 0; i < n; i++) { for (int j = 0; j < m; j++) { if (student_answer[i][j] == sub[j].choice)//完全正确 total[i] += sub[j].grade; else { flag = 0;//有人错了 tmp = student_answer[i][j];//学生答案 string s = sub[j].choice;//正确答案 int len = tmp.size(); for (int k = 0; k < len; k++) { int t = s.find(tmp[k]);//字符位置 if (t!=s.npos) { s.erase(t, 1); tmp.erase(k, 1); k--; len--; } } if (tmp.empty())//答对一部分的情况 { total[i] += sub[j].grade / 2;//把一半分数加上 for (int k = 0; k < s.size(); k++) sub[j].wrong_answer[s[k] - 'a']++;//统计错误选项 } else//选错一分得不到 { for (int k = 0; k < s.size(); k++) sub[j].wrong_answer[s[k] - 'a']++;//统计错误选项 for (int k = 0; k < tmp.size(); k++) sub[j].wrong_answer[tmp[k] - 'a']++; } } } } for (int i = 0; i < n; i++) printf("%.1lf\n", total[i]); if (flag) cout << "Too simple"; else { int max = 0; for (int i = 0; i < m; i++)//遍历每一道题,寻找错的最多的次数 { for (int j = 0; j < 5; j++) if (sub[i].wrong_answer[j] > max) max = sub[i].wrong_answer[j]; } for (int i = 0; i < m; i++) { for (int j = 0; j < 5; j++) { if (sub[i].wrong_answer[j] == max) cout << max << " "<<i+1<<"-"<<(char)(j+'a')<<endl; } } } return 0; }