基于dplyr/tidyverse自动化生成区域袋订单的数据框处理求助
自动化水果袋订单处理解决方案
首先解决你最初的函数报错问题:原naming.fun无法处理整列向量,因为mutate_all会将整列传递给函数,而非单个值。下面是完整的自动化流程,从数值转水果名称、合并数据集到最终按袋拆分的全步骤:
1. 数值列转重复水果名称
定义通用函数处理数值到水果名称的转换,支持向量输入,同时统一名称小写:
library(dplyr) library(purrr) # 输入数值向量和水果名称,输出重复水果名称的字符串向量(0对应空字符串) num_to_fruit <- function(num_vec, fruit_name) { map_chr(num_vec, ~if (.x == 0) "" else paste(rep(tolower(fruit_name), .x), collapse = " ")) } # 处理各数据集的数值列 Apples_processed <- Apples %>% mutate(across(area1:area2, ~num_to_fruit(.x, "Apple"))) Peaches_processed <- Peaches %>% mutate(across(area1:area3, ~num_to_fruit(.x, "Peach"))) Pears_processed <- Pears %>% mutate(across(area1, ~num_to_fruit(.x, "Pear")))
2. 合并数据集到统一结构
按bag合并三个数据集,补全缺失的区域列并填充空字符串,同时对齐bag顺序:
Final_merged <- list(Apples_processed, Peaches_processed, Pears_processed) %>% reduce(full_join, by = "bag") %>% group_by(bag) %>% summarise(across(starts_with("area"), ~paste(na.omit(.), collapse = " ")), .groups = "drop") %>% mutate(area3 = ifelse(is.na(area3), "", area3)) %>% arrange(factor(bag, levels = c("orange", "yellow", "green", "blue", "purple")))
这一步得到的Final_merged就是你示例中要求的中间结构数据集。
3. 按袋规则拆分并格式化
实现“每袋同一种水果仅一个”的拆分逻辑,统计每种水果所需袋数并格式化为指定样式:
# 将水果字符串转换为袋分配格式的函数 format_bags <- function(fruit_str) { if (fruit_str == "") return("") # 拆分字符串并统计每种水果的数量 fruit_counts <- table(strsplit(fruit_str, " ")[[1]]) max_count <- max(fruit_counts) # 按袋分配水果,每袋可包含多种但同一种仅一个 bag_contents <- map(1:max_count, ~names(fruit_counts)[fruit_counts >= .x]) %>% keep(~length(.x) > 0) %>% map_chr(~paste(.x, collapse = "/")) # 统计相同袋内容的重复次数,格式化输出 bag_counts <- table(bag_contents) paste(map2_chr(names(bag_counts), as.integer(bag_counts), ~paste0(.y, ": ", .x)), collapse = ", ") } # 应用格式化函数到所有区域列 Final_result <- Final_merged %>% mutate(across(starts_with("area"), format_bags)) # 查看最终结果 print(Final_result)
运行上述代码后,Final_result将完全匹配你提供的理想输出格式。
内容的提问来源于stack exchange,提问作者Schatzi121
相关产品推荐
相关产品推荐

