R/dplyr:将两行数据转换为两列
嘿,这个需求很常见,用R的tidyverse工具链或者基础函数都能轻松实现,我给你写两种直接能用的方案:
方法1:用tidyr::pivot_wider(推荐,代码更直观)
首先先构造你的原始数据框(方便你测试):
# 构造原始数据 df <- data.frame( Word = c("shoe", "shoes", "toy", "toys", "key", "keys", "jazz"), Base = c("shoe", "shoe", "toy", "toy", "key", "key", "jazz"), Number = c(4834, 49955, 75465, 23556, 39485, 6546, 58765), Type = c("singular", "plural", "singular", "plural", "singular", "plural", "plural"), stringsAsFactors = FALSE )
然后用pivot_wider做宽表转换,同时调整列名和顺序:
library(tidyr) library(dplyr) # 转换并整理数据 result <- df %>% # 按Base分组,把Type的不同值转成列 pivot_wider( id_cols = Base, names_from = Type, values_from = c(Word, Number), # 缺失的单复数用NA填充 values_fill = list(Word = NA_character_, Number = NA_integer_) ) %>% # 重命名列名匹配你的需求 rename( Word_Sg = Word_singular, Word_Pl = Word_plural, Num_Singular = Number_singular, Num_Plural = Number_plural ) %>% # 调整列的顺序和你要的一致 select(Word_Sg, Word_Pl, Base, Num_Singular, Num_Plural) # 查看结果 print(result)
运行后输出就是你想要的结构:
Word_Sg Word_Pl Base Num_Singular Num_Plural 1 shoe shoes shoe 4834 49955 2 toy toys toy 75465 23556 3 key keys key 39485 6546 4 NA jazz jazz NA 58765
方法2:Base R 实现(无需加载额外包)
如果你不想加载tidyverse包,用基础R的reshape函数也能完成:
# Base R 转换 result_base <- reshape( df, idvar = "Base", timevar = "Type", direction = "wide", v.names = c("Word", "Number") ) # 重命名列名 colnames(result_base) <- gsub("Word\\.(singular|plural)", "Word_\\1", colnames(result_base)) colnames(result_base) <- gsub("Number\\.(singular|plural)", "Num_\\1", colnames(result_base)) colnames(result_base) <- gsub("singular", "Sg", colnames(result_base)) colnames(result_base) <- gsub("plural", "Pl", colnames(result_base)) # 调整列顺序并替换空值为NA result_base <- result_base[, c("Word_Sg", "Word_Pl", "Base", "Num_Sg", "Num_Pl")] result_base[result_base == ""] <- NA print(result_base)
这个方法的输出和第一种完全一致,适合环境受限不能加载包的场景。
内容的提问来源于stack exchange,提问作者rayne
相关产品推荐
相关产品推荐

