R语言频率表取整求助:arsenal包tableby函数取整方案
问题:arsenal包tableby函数频数取整及替代方案
我在R/RMarkdown中使用arsenal包的tableby()生成频率表,该工具便于集成到docx/html文档中,但需要将频数取整至最接近的5或10。尝试通过tableby.control()设置digits=-1失败,系统提示digits需≥0。
模拟数据集与常规表生成流程
set.seed(1234) library(dplyr) library(arsenal) x1 <- c(rep("Man",40),rep("Woman",60)) %>% as.factor() x2 <- sample(c("Sick","Healthy"),100,replace=TRUE) %>% as.factor() df <- data.frame(x1,x2) Control_notrounded <- tableby.control(digits=0,digits.pct=2,cat.stats=c("countpct","Nmiss2")) table <- tableby(x1~x2,control=Control_notrounded,data=df) print(summary(table))
失败的取整尝试
Control_rounded <- tableby.control(digits=-1,digits.pct=2,cat.stats=c("countpct","Nmiss2")) table2 <- tableby(x1~x2,control=Control_rounded,data=df) print(summary(table2))
可行解决方案
方案1:手动处理arsenal生成的表格结果
arsenal的summary()输出可转换为数据框,之后手动对频数进行取整处理:
# 生成原始表 set.seed(1234) library(dplyr) library(arsenal) x1 <- c(rep("Man",40),rep("Woman",60)) %>% as.factor() x2 <- sample(c("Sick","Healthy"),100,replace=TRUE) %>% as.factor() df <- data.frame(x1,x2) Control_notrounded <- tableby.control(digits=0,digits.pct=2,cat.stats=c("countpct","Nmiss2")) table <- tableby(x1~x2,control=Control_notrounded,data=df) tab_summary <- summary(table, text=TRUE) # 转换为数据框 tab_df <- as.data.frame(tab_summary) # 定义取整函数(可切换取整到5或10) round_to_nearest <- function(x, nearest=5) { round(x/nearest)*nearest } # 拆分、取整、重组频数与百分比 tab_df <- tab_df %>% mutate( count = as.numeric(sub("^(\\d+) \\((.*)\\)$", "\\1", `x2`)), pct = sub("^(\\d+) \\((.*)\\)$", "\\2", `x2`), count_rounded = round_to_nearest(count), x2 = paste0(count_rounded, " (", pct, ")") ) %>% select(-count, -pct, -count_rounded) # 输出处理后的表格 print(tab_df, row.names=FALSE)
方案2:使用替代包生成带取整频数的表格
用gtsummary包(支持docx/html导出)
gtsummary支持自定义统计量格式,可直接嵌入取整逻辑:
library(gtsummary) # 定义取整函数 round_to_nearest <- function(x, nearest=5) { round(x/nearest)*nearest } # 生成带取整频数的表格 df %>% tbl_summary( by = x1, statistic = list(all_categorical() ~ "{round_to_nearest(n)} ({p}%)"), digits = list(all_categorical() ~ c(0, 2)) ) %>% as_flex_table() # 可导出为docx/html格式
用flextable+dplyr自定义生成表格
完全自定义表格内容,灵活性更高:
library(flextable) # 计算频数、百分比并取整 freq_table <- df %>% group_by(x1, x2) %>% summarise(n = n(), .groups = "drop") %>% group_by(x1) %>% mutate(pct = round(n/sum(n)*100, 2)) %>% ungroup() %>% mutate(n_rounded = round_to_nearest(n)) %>% mutate(label = paste0(n_rounded, " (", pct, "%)")) %>% pivot_wider(names_from = x1, values_from = label) # 转换为可导出的表格 freq_table %>% flextable() %>% autofit()
内容的提问来源于stack exchange,提问作者She Wonders
相关产品推荐
相关产品推荐

