解题思路参考柳婼
#include<iostream>
#include<vector>
using namespace std;
int main(){
int n,m;
cin>>n>>m;
int hash[5]={1,2,4,8,16}; //选项个数不超过5个
vector<int> fullscore(m),trueopthash(m);
int optnum,trueoptnum;
char opt;
for(int i=0;i<m;i++){
cin>>fullscore[i]>>optnum>>trueoptnum;
for(int j=0;j<trueoptnum;j++){
scanf(" %c",&opt);
trueopthash[i]+=hash[opt-'a']; //根据二进制位1所在的位置判断选择了哪些选项
}
}
vector<vector<int>> cnt(m,vector<int>(5));
for(int i=0;i<n;i++){
double score=0.0;
for(int j=0;j<m;j++){
int selnum,selopthash=0;
getchar(); //吃掉回车
scanf("(%d",&selnum);
for(int k=0;k<selnum;k++){
scanf(" %c",&opt);
selopthash+=hash[opt-'a'];
}
scanf(")");
int el=selopthash^trueopthash[j];//^二进制异或运算,二进制位相同对应位结果为0,不同对应位结果为1
if(!el) score+=fullscore[j]; //选项全正确
else{
if((selopthash|trueopthash[j])==trueopthash[j]) //选项部分正确,注意加括号(selopthash|trueopthash[j])
score+=fullscore[j]*1.0/2; //|二进制或运算,只要二进制位有一个为1,则对应位结果为1
for(int k=0;k<5;k++) //找出错误选项号
if(el&hash[k]) cnt[j][k]++; //&二进制与运算,二进制位都为1,对应位结果才为1
}
}
printf("%.1f\n",score);
}
int maxcnt=0;
for(int i=0;i<m;i++)
for(int j=0;j<5;j++)
if(cnt[i][j]>maxcnt) maxcnt=cnt[i][j];
if(maxcnt==0) cout<<"Too simple"<<endl;
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;
}