1073 多选题常见计分法 (20 分)

捕获.PNG

#include <iostream>
#include<string>
#include<vector>
#include<cstdio>
#include<cmath>
using namespace std;
int n, m, optnum, truenum, temp, maxcnt = 0;

int opt[1010][110] = {0};//代表着每个学生对每个题目的选择
char c;
int main()
{
	int hash[] = { 1,2,4,8,16 };//分别代表00001,00010,00100,01000,10000
	scanf("%d %d", &n,&m);
	vector<int> fullscore(m), trueopt(m);//每个题目的满分和正确选项
	vector<vector<int>> cnt(m, vector<int>(5));//记录每个题目每个选项的错误数量
	for (int i = 0;i < m;i++) {
		scanf("%d %d %d", &fullscore[i], &optnum, &truenum);
		for (int j = 0;j < truenum;j++) {
			cin >> c;//cin之后会有换行遗留在缓冲区内
			trueopt[i] +=hash[ c - 'a'];
		}
	}
	for (int i = 0;i < n;i++) {
		double grade = 0;
		for (int j = 0;j < m;j++) {
			getchar();//吃掉上一次留在缓冲区内的换行
			if (j != 0)scanf(" ");
			scanf("(%d", &temp);
			for (int k = 0;k < temp;k++) {
				scanf(" %c", &c);
				opt[i][j] += hash[c - 'a'];
			}
			scanf(")");//scanf()之后会有换行遗留在缓冲区内
			int el = opt[i][j] ^ trueopt[j];//相同则为0,相异则为1
			if (el) {
				if ((opt[i][j] | trueopt[j]) == trueopt[j]) {//缺选
					grade = grade + (double)fullscore[j] / 2;
				}
				if (el) {
					for (int k = 0;k < 5;k++)
						if (el&hash[k])cnt[j][k]++;
				}
			}
			else {
				grade += fullscore[j];
			}
		}
		printf("%.1lf\n", grade);
	}
	for (int i = 0;i < m;i++) {
		for (int j = 0;j < 5;j++) {
			maxcnt = maxcnt > cnt[i][j] ? maxcnt : cnt[i][j];
		}
	}
	if (maxcnt == 0) {
		cout << "Too simple";
	}
	else {
		for (int i = 0;i < m;i++) {
			for (int j = 0;j < 5;j++) {
				if (cnt[i][j] == maxcnt) {
					printf("%d %d-%c\n", maxcnt, i + 1, j + 'a');
				}
			}
		}
	}
	return 0;
	
}

参考博客:https://www.liuchuo.net/archives/4216

posted @ 2019-03-03 11:19  Chance-Zou  阅读(788)  评论(0编辑  收藏  举报