1058 选择题 (20 point(s))

#include <bits/stdc++.h>
using namespace std;

struct Question{
	int score, num, cor;
	set<char> copt;
};

int main() {
	// 批改选择题 指出错误人数最多题目
	// 输入 学生人数 多选题个数
	int n, m;
	vector<Question> qt;
	cin >> n >> m; 
	
	// M行给出 
	// 满分值≤5 2≤选项个数≤5 ≥ 正确选项个数 正确选项
	// 选项 a- 
	for(int i = 0; i < m; i++){
		int score, num, cor;
		Question tmp;
		cin >> score >> num >> cor;
		tmp = {score, num, cor};
		// 循环插入正确选项 
		while(cor--){
			char c;
			cin >> c; 
			tmp.copt.insert(c);
		}
			
		// 全部输入完之后存入题目 
		qt.push_back(tmp);
	}
	 
	// N行给出 
	// 记录错题人数
	int fault[m]{0}; 
	while(n--){
		// 遍历每个题目 初始化成绩 题目编号  
		int sum = 0, i = 0;
		for(auto q : qt){
			int num, all = 0, flag = true;
			char c;
			// 吃掉没意义的括号 读取 答题选项数量 
			cin >> c >> num;
			
			// 有选项的时候执行 
			while(num--){
				// 读取选中选项(按题序给出
				cin >> c;
				// 有一个题错误不得分  
				if(q.copt.find(c) == q.copt.end())
					flag = false;
				// 字符选项需要全部录入 否则会多出字符导致后面错误
				
				// 第一题++
				all++; 
			}
				
			// 没选中全部不得分 
			if(all != q.cor) flag = false;
			 
			// 全部正确才得分
			if(flag) sum += q.score;
			// 统计错题 
			else fault[i]++;
			
			// 吃掉没意义的括号
			cin >> c;
			
			//指向下一题
			i++; 
		} 
		
		// 每个人最后直接评出分数
		cout << sum << endl; 
	}
	
	// 找出最大值
	int max = *max_element(fault, fault + m);
	
	// 没有人错误  Too simple
	if(max == 0) cout << "Too simple";
	// 并列 空格分割 编号递增输出 一次次数 多个编号
	else{
		cout << max; 
		int i = 1;
		for(auto f: fault){
			// 编号 1开始
			if(f == max)
				cout << " " << i;
			//指向下一题 
			i++;
		}
	}
}

代码有点长,写了有点久75min左右,前面犯了一些问题,自己定义的变量和题目要求的没能够明确清楚,导致卡了十分钟左右。所以多写写注释或者在草稿纸上面明确下还是很有必要的,多理解下题目和里面的变量。

不然多看两眼或者写一两行字也就一两分钟,但是找bug找十分钟。显然得不偿失。

中间判断正确也卡了一下,刚开始只记得要判断学生的选项有没有选对,但是题目还有一个条件就是“全部正确才能得到该题的分数”,所以不仅仅是学生还有题目的正确选项需要考虑。

刚开始想复杂了,还想着要遍历全部正确选项然后对着学生的选项。但后面想了想完全没必要,因为已经给出了正确选项的个数(写的时候一时忘记了),只需要声明一个变量记录学生正确个数,对比题目正确选项个数即可。

除了模拟过程中繁琐了一点,但是把所有都搞定之后直接就全AC了。关键还是在某些细节上面卡了不少时间。虽然有在代码里面先照着题目给出大体的思路,但是具体的实现没有明确清楚,比如题目编号的因为题目没有给出,还得自己记录一下,当时当时没有明确到底在那个代码块 {} 大括号里面声明变量,又应该在哪里变更变量指向下一题,所以又花了点时间试错改正。

或者就像刚开始弄错变量导致调试,或者是中间的判读选项正确。这些如果能够在草稿上面进一步明确处理的方式,可能可以节省不少时间。至少进一步推导也能够明确自己能否解决这个问题,是否在具体过程中存在某些无法解决的,自己又难以给出方法的细节问题。这时候就可以跳过不管,直接下一题了。而不需要在实现的时候才发现有问题,但这时候已经浪费不少时间了。

在解题上,我们先判断这题目是有难度的,比如像螺旋矩阵那题,一看到题目的条件我们去尝试给出自己的思路,是否能够想到什么解决的方法,是否能够想起有什么类似的解题思路。如果很陌生的,或者觉得给出的数据很复杂的,就应该判断这题目是具有一定难度的,不像一般的题目一两个过程就能够解决的。

对于这类题目,就应该在草稿纸上先尝试给出具体过程的实现,尝试检查题目给出的所有条件,将这种复杂问题具体化明确化。就算发现具体实现给不出,也能够快速反应过来,感觉去做那些可以做的题目,而不用白费时间在上面。


读取题目信息的时候,因为包含一个容器,所以可以对结构体一部分变量进行赋值,如下。

tmp = {score, num, cor};

然后再对剩下的容器读取元素。


cin >> c 开始的时候忘记写这个东西了,而且因为没有正确明确变量把 while(cor--) 读取正确选项弄成了 num,全部选项个数。导致了 Running Error 。

不过如果是不读取 cin 的话,其实就算输入了也不会卡住的,直接就跳过你的输入继续执行下面的代码了。但是如果读取了错误的循环变量,导致循环变量没有正确执行的话,就会变成死循环导致 Running Error 。

所以以后出现这个评测错误的时候,应该注意自己的循环退出循环条件是不是写错了。

1058 选择题 (20 point(s))

上一篇:el-date-picker TimePicker 时间选择器


下一篇:Git最强总结!