【问题标题】:How to split dataframe column in R如何在R中拆分数据框列
【发布时间】:2015-08-28 15:27:20
【问题描述】:

我在名为 parm_value 的数据框中有一列,我想根据字段中下划线的位置将其分成两列,下界和上界。我一直在尝试使用 grep 和 substring 的组合但没有成功

当前数据帧格式:

   parm_value
1       30_34
2       60_64
3       65_69
4       75_79
5       90_94

所需的数据帧格式:

   parm_value   lower_bound   upper_bound
1       30_34            30            34
2       60_64            60            64
3       65_69            65            69
4       75_79            75            79
5       90_94            90            94

我一直在尝试类似的东西

dat02 <-
   dat01 %>%
   mutate(lower_bound = substring(parm_value, 1, grep("_", parm_value) - 1)

【问题讨论】:

    标签: r substring


    【解决方案1】:

    如果你的data.frame被称为df,你可以试试:

    cbind(df, `colnames<-`( do.call("rbind", sapply(df[,1], strsplit, "_")), c("lower bound", "upper bound")))
    
      #    parm_value lower bound upper bound
      #  1      30_34          30          34
      #  2      60_64          60          64
      #  3      65_69          65          69
      #  4      75_79          75          79
      #  5      90_94          90          94
    

    【讨论】:

      【解决方案2】:

      使用strsplit:

      library(data.table)
      xmpl <- data.table(val = rep("65_45", 5))
      xmpl[ , lower := sapply(strsplit(val, "_"), "[[", 1)]
      xmpl[ , upper := sapply(strsplit(val, "_"), "[[", 2)]
      
      xmpl
      #      val lower upper
      # 1: 65_45    65    45
      # 2: 65_45    65    45
      # 3: 65_45    65    45
      # 4: 65_45    65    45
      # 5: 65_45    65    45
      

      如果它是一个非常大的表,您可以通过只运行一次strsplit,然后在定义新的data.table 字段时调用该对象来节省运行时间。

      strsplit 返回一个列表:

      strsplit("65_45", "_")
      # [[1]]
      # [1] "65" "45"
      

      sapply 调用使用子集函数 [[ 选择第 N 项遍历列表,其中 N 在 sapply 中给出为 sapply(some_list, "[[", N)

      【讨论】:

      • 1.9.5 有一个函数tstrsplit 可以拆分和转置结果,这使得这个操作很简单:setDT(df)[, c("l", "h") := tstrsplit(parm_value, "_", fixed=TRUE)]
      • @Arun 太棒了。期待1.9.6
      【解决方案3】:

      你也可以使用splitstackshape中的cSplit

      library(splitstackshape)
      out = cbind(dat, setnames(cSplit(dat, "parm_value", "_", fixed = FALSE),
            c("lower_bound", "upper_bound")))
      
      #> out
      #  parm_value lower_bound upper_bound
      #1      30_34          30          34
      #2      60_64          60          64
      #3      65_69          65          69
      #4      75_79          75          79
      #5      90_94          90          94
      

      【讨论】:

        【解决方案4】:

        试试read.table

        cbind(df1[1],read.table(text= as.character(df1$parm_value), sep="_", 
                     col.names=c('lower_bound', 'upper_bound')))
        #    parm_value lower_bound upper_bound
        #1      30_34          30          34
        #2      60_64          60          64
        #3      65_69          65          69
        #4      75_79          75          79
        #5      90_94          90          94
        

        separate 来自tidyr

        library(tidyr)
        separate(df1, parm_value, into=c('lower_bound', 'upper_bound'), remove=FALSE)
        #    parm_value lower_bound upper_bound
        #1      30_34          30          34
        #2      60_64          60          64
        #3      65_69          65          69
        #4      75_79          75          79
        #5      90_94          90          94
        

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 2016-06-27
          • 1970-01-01
          • 1970-01-01
          • 2014-09-02
          • 1970-01-01
          • 2013-05-27
          • 1970-01-01
          相关资源
          最近更新 更多