无需逐行编码,灵活生成多测验场景下的缺失答题密钥
批量生成多套测验的答题密钥(适配任意题量)
核心思路是自动配对每道题的ansXX(答案列)和binXX(得分列),按test分组后计算答对者的答案均值作为密钥,无需逐题硬编码,完全适配任意题量的测验。
方法1:长格式数据批量处理(直观易上手)
先把宽表转成便于分组处理的长格式,完成计算后再转回宽表,逻辑清晰,新手也能快速理解:
library(tidyverse) # 原始数据集 df <- data.frame(id =c(1, 2, 3, 4, 5, 6, 7, 8, 9,10), # 参与者ID test =c(1, 1, 1, 1, 1, 2, 2, 2, 2, 2), # 测验套组ID ans01=c(1, 2, 3, 4, 1, 1, 2, 3, 3, 4), # 第1题原始答案 ans02=c(2, 2,NA, 3, 4, 4, 3, 1, 1, 2), # 第2题原始答案 bin01=c(1, 0, 0, 0, 1, 0, 1, 0, 0, 0), # 第1题得分(1=答对) bin02=c(1, 1, 0, 0, 0, 1, 0, 0, 0, 0)) # 第2题得分 # 批量生成密钥 key_data <- df %>% # 转长格式:自动把ansXX和binXX配对,提取题号 pivot_longer(cols = -c(id, test), names_to = c(".value", "question"), names_pattern = "(ans|bin)(\\d+)") %>% # 只保留答对的记录 filter(bin == 1) %>% # 按测验套组+题号分组,计算答对者的答案均值作为密钥 group_by(test, question) %>% summarise(key = mean(ans, na.rm = TRUE), .groups = "drop") %>% # 转回宽表,恢复keyXX的命名格式 pivot_wider(names_from = question, names_prefix = "key", values_from = key) print(key_data)
这种方法不需要手动指定题号,只要ans和bin的命名规则统一(比如ans03对应bin03),不管新增多少道题,代码都能自动处理。
方法2:宽表直接批量处理(高效简洁)
用dplyr的across函数结合字符串匹配,直接在原宽表上操作,代码更紧凑,适合熟悉dplyr的用户:
library(dplyr) library(stringr) # 原始数据集(同上) df <- data.frame(id =c(1, 2, 3, 4, 5, 6, 7, 8, 9,10), test =c(1, 1, 1, 1, 1, 2, 2, 2, 2, 2), ans01=c(1, 2, 3, 4, 1, 1, 2, 3, 3, 4), ans02=c(2, 2,NA, 3, 4, 4, 3, 1, 1, 2), bin01=c(1, 0, 0, 0, 1, 0, 1, 0, 0, 0), bin02=c(1, 1, 0, 0, 0, 1, 0, 0, 0, 0)) # 自动提取所有题号(从ans列的命名中提取数字) question_nums <- str_extract(names(df)[startsWith(names(df), "ans")], "\\d+") # 批量生成密钥 key_data <- df %>% group_by(test) %>% summarise( # 遍历每道题的ans列,找到对应bin列,计算答对者的答案均值 across(paste0("ans", question_nums), ~ mean(.x[get(paste0("bin", str_extract(cur_column(), "\\d+"))) == 1], na.rm = TRUE), .names = "key{str_extract(.col, '\\d+')}") ) print(key_data)
关键优势
两种方法都完全适配未来的扩展需求:只要新增的题目遵循ansXX(答案)+binXX(得分)的命名规则,代码无需任何修改就能自动处理。
内容的提问来源于stack exchange,提问作者BoTz
相关产品推荐
相关产品推荐

