【问题标题】:Incremental increase in row values until change in adjacent column found行值的增量增加,直到找到相邻列的变化
【发布时间】:2020-08-20 20:52:30
【问题描述】:

我需要分解调查数据以允许重复答案。

现有数据集:

       initial_value
row1        1
row2        1
row3        1
row4        2
row5        3
row6        3

我希望创建一个重复的列,增量为 0.1,直到发现值发生变化:

       initial_value    desired_value
row1        1                1.1
row2        1                1.2
row3        1                1.3 
row4        2                2.1
row5        3                3.1
row6        3                3.2
row7        3                3.3

【问题讨论】:

  • 这也适用于dplyrdf %>% group_by(initial_value) %>% mutate(delta=as.numeric(paste0(initial_value,'.',1:n())))
  • 使用row_number() 而不是1:n()

标签: r dataframe tidyverse


【解决方案1】:

使用分组和.N 的另一个data.table 解决方案:

library(data.table) 

setDT(df1)[, desired_value := initial_value + seq_len(.N) * 0.1, .(initial_value)][]
#>    initial_value desired_value
#> 1:             1           1.1
#> 2:             1           1.2
#> 3:             1           1.3
#> 4:             2           2.1
#> 5:             3           3.1
#> 6:             3           3.2
#> 7:             3           3.3

dplyr 解决方案也可以更简单:

library(dplyr)

df1 %>% 
  group_by(initial_value) %>% 
  mutate(desired_value = initial_value + row_number() * 0.1)

【讨论】:

    【解决方案2】:

    一个选项是在按base R 中的“初始值”分组后使用seq

    df1$desired_value <-  with(df1, ave(initial_value, initial_value, 
        FUN = function(x) seq(x[1] + 0.1, length.out = length(x), by = .1)))
    

    或者使用pasterowid 来自data.table

    library(data.table)
    setDT(df1)[, desired_value := as.integer(paste0(intial_value, ".", 
           rowid(initial_value)))]
    

    数据

    df1 <- structure(list(initial_value = c(1L, 1L, 1L, 2L, 3L, 3L, 3L)),
    class = "data.frame", row.names = c("row1", 
    "row2", "row3", "row4", "row5", "row6", "row7"))
    

    【讨论】:

      【解决方案3】:

      这是另一个使用 ave 的基本 R 选项

      within(df,desired_value <- initial_value+0.1*ave(1:nrow(df),initial_value,FUN = seq_along))
      

      给了

           initial_value desired_value
      row1             1           1.1
      row2             1           1.2
      row3             1           1.3
      row4             2           2.1
      row5             3           3.1
      row6             3           3.2
      row7             3           3.3
      

      【讨论】:

        【解决方案4】:

        使用此解决方案,即使每个标识符的行数超过 10 行,您也很灵活。

        library(dplyr)
        
        df <- data.frame(initial_value = c(1,1,1,2,3,3,3,rep(4, 20)))
        
        df %>%
            group_by(initial_value) %>% 
            mutate(desired_value = initial_value + row_number() / 10^(ceiling(log10(n()+0.1)))) %>% 
            ungroup()
        

        【讨论】:

        • 为什么你有这一切row_number() / 10^(ceiling(log10(n()+0.1)))
        • 以防万一你有 10+ 行.. 它会自动除以最接近的 10 次方。
        • 你能用一个例子来展示它与我对 dplyr 的行为有何不同吗?
        • 我已经留下了一个例子,其中 4 重复了 20 次。尝试用你的代码和这个代码运行相同的例子 :)
        猜你喜欢
        • 2017-12-06
        • 1970-01-01
        • 2017-04-18
        • 2018-01-18
        • 2017-10-11
        • 1970-01-01
        • 1970-01-01
        • 2020-09-28
        相关资源
        最近更新 更多