【问题标题】:delimit into rows for every combination between two columns of unbalance elements with dplyr or data.table?使用 dplyr 或 data.table 为两列不平衡元素之间的每个组合分隔成行?
【发布时间】:2021-04-19 21:21:35
【问题描述】:

嗨,假设我有一个这样的数据框,

df = data.frame ( 
  color = c("blue")
  ,sample = c( "A")
  ,size = c("L,S,XL")
  , sex = c ( "M,F") 
  )
 color sample   size sex
1  blue      A L,S,XL M,F

理想情况下,我希望通过分隔大小和性别将其拆分为新行。 以便新的数据框看起来像这样。

  color sample size sex
1  blue      A    L   M
2  blue      A    L   F
3  blue      A    S   M
4  blue      A    S   F
5  blue      A   XL   M
6  blue      A   XL   F

我尝试用这种方式拆分它,但它会导致一些错误。

df %>% tidyr::separate_rows(size, sex)  %>% data.frame()

【问题讨论】:

  • 基本 R 选项:expand.grid(lapply(df, function(x) unlist(strsplit(x, split = ","))))

标签: r dplyr data.table


【解决方案1】:

看起来错误是由于大小和性别列是factors。使用as.character 将这些列转换为字符串,然后您的代码应该可以工作。但是请注意,该函数不允许每列有不同的长度(即,性别有 2 个唯一值,大小有 3 个),因此您必须一一进行。

df$size <- as.character(df$size)
df$sex  <- as.character(df$sex)

(df.new <- df %>% tidyr::separate_rows(size) %>% tidyr::separate_rows(sex))

【讨论】:

    【解决方案2】:

    试试tidyr包的separate_rows函数:

    library(tidyr)
    df %>% separate_rows(color,sep=",") %>%
          separate_rows(sample,sep=",") %>%
          separate_rows(size,sep=",") %>%
          separate_rows(sex,sep=",")
    

    【讨论】:

      【解决方案3】:

      这是使用data.table包中的函数CJ或内置函数expand.grid的另一种解决方案:

      使用data.table

      library(data.table)
      
      do.call(CJ, sapply(df, strsplit, ","))
      
      #    color sample size sex
      # 1:  blue      A    L   F
      # 2:  blue      A    L   M
      # 3:  blue      A    S   F
      # 4:  blue      A    S   M
      # 5:  blue      A   XL   F
      # 6:  blue      A   XL   M
      

      使用内置函数

      expand.grid(sapply(df, strsplit, ","))
      
      #   color sample size sex
      # 1  blue      A    L   M
      # 2  blue      A    S   M
      # 3  blue      A   XL   M
      # 4  blue      A    L   F
      # 5  blue      A    S   F
      # 6  blue      A   XL   F
      

      【讨论】:

        猜你喜欢
        • 2016-11-08
        • 2014-04-18
        • 2019-08-01
        • 1970-01-01
        • 1970-01-01
        • 2014-02-03
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多