問題背景
設計一套試卷,裡面有單選,多選,判斷題(實際上判斷題就是兩個選項的單選題而已)
其他都很好處理,
裡面的關鍵點,顯然是多選題的錯選、漏選、以及選對該如何處理
這裡提供了一種方案,個人感覺比較合理。
思路和方案
- 選項用2^n的整數值表示
- 判斷對錯用位元算
- 多選題如果沒選全,則看選對了的數目占正确答案的選項數目的比例
- 可設定題目分數是否一定為整數還是可以是0.5的倍數
方案
using System;
using System.Diagnostics;
using Microsoft.VisualStudio.TestTools.UnitTesting;
namespace Web.Test.BinaryTest
{
[Flags]
public enum Options
{
O = 0,
A = 1,
B = 1 << 1,
C = 1 << 2,
D = 1 << 3
}
[TestClass]
public class UnitTest1
{
[DataRow(Options.O)] //空
[DataRow(Options.A)] //無錯,未選全
[DataRow(Options.B)] //無錯,未選全
[DataRow(Options.C)] //無錯,未選全
[DataRow(Options.A | Options.B)]//無錯,未選全
[DataRow(Options.A | Options.C)]//無錯,未選全
[DataRow(Options.B | Options.C)]//無錯,未選全
[DataRow(Options.A | Options.B | Options.C)]//對
[DataRow(Options.A | Options.B | Options.D)]//有對有錯,算錯
[DataRow(Options.C | Options.B | Options.D)]//有對有錯,算錯
[DataRow(Options.C | Options.A | Options.D)]//有對有錯,算錯
[DataRow(Options.A | Options.B | Options.C | Options.D)]//有對有錯,算錯
[TestMethod]
public void TestMethod1(Options option, bool isIntegerPoint = false)
{
//isIntegerPoint 為true時,每道題隻有整數得分值;否則,可以為0.5的倍數的得分值
int totalScore = 4;
int totalAnswer = (int)(Options.A | Options.B | Options.C | Options.D); //ABCD
int rightAnswer = (int)(Options.A | Options.B | Options.C); //ABC
int wrongAnswer = totalAnswer - rightAnswer;
double score;
var intOption = (int)option;
//選對時
if (rightAnswer == intOption)
{
score = totalScore;
Debug.WriteLine($"score = {score}");
}
//選錯時
else if ((wrongAnswer & intOption) > 0)
{
score = 0;
Debug.WriteLine($"score = {score}");
}
//未錯,但未選全時
else
{
var rightOptionsCount = Convert.ToString(rightAnswer, 2).Replace("0", "").Length; //總選項數
var userOptionsCount = Convert.ToString(intOption, 2).Replace("0", "").Length; // 使用者選項數
//整數分值
if (isIntegerPoint)
{
var point = totalScore * userOptionsCount / rightOptionsCount;
score = point;
}
//0.5的倍數的分值
else
{
var point = (double)(totalScore * userOptionsCount) / rightOptionsCount;
score = Math.Round((2 * point), MidpointRounding.AwayFromZero);
}
Debug.WriteLine($"score = {score / 2}");
}
}
}
}