将前一行的值与当前行相加,并在添加

时间:2019-01-15 13:56:22

标签: r

在R中,我有一个数据帧D1。它包含“ ID”和“ Case”列。 ID具有重复的值,并且大小写包含“ NA”和“ Up”。

D1

ID case 
aa NA   
aa NA    
aa Up    
aa NA    
cc NA    
cc NA    
dd NA    
dd NA    
dd Up    
dd NA    
dd NA    
dd NA    
ee NA    
ee NA    
ee NA    
ff up    
ff NA    
gg NA        

所以我的要求是在我想要的位置创建一个新列“ Deep”:

  1. 创建一个新列“ Deep”,其值为0。

  2. 其次,确定每个组的ID的第一个观察值,并将其在“ Deep”列下指定为0。  例如,第一个“ aa”将始终为“ 0”。  尽管它不会影响“ Deep”列的视图,因为它仍然很深  列作为0值。

  3. 第三,从“ case”列中标识值“ Up”,并将其添加为1。 因此,当case == up时,则为deep + 1,因此输出将为Deep = 1。

  4. 第四,保留由逻辑'case =='Up'创建的值,即为'1',并将其加1,直到出现相同的'Id'。 因此所有在case =='Up'之后具有相同'Id'的值将添加前一行值+ 1 id deep = 2,依此类推。

请注意,随着ID的每次更改,“深度”下的新值将变为0。

下面是我想要的输出

ID case deep
aa NA    0
aa NA    0
aa Up    1
aa NA    2
cc NN    0
cc NN    0
dd NA    0
dd NA    0
dd Up    1
dd NA    2
dd NA    3
dd NA    4
ee NA    0
ee NA    0
ee NA    0
ff up    1
ff NA    2
gg NA    0    

在这里您可以看到使用'Deep'创建的新列。

  1. 任何新ID的首次出现都等于0。
  2. case == upper的值将为1,然后是所有加1的值,直到id不变或找不到其他ID。
  3. 当找到新的id且大小写也为大写时,则Deep的值将为1,例如'ff'的值为1。

请帮助我

2 个答案:

答案 0 :(得分:3)

我们通过'ID'分组,获得用str_detect创建的逻辑向量的累加和,并用累加和包装以添加1个值

library(tidyverse)
D1 %>% 
  group_by(ID) %>% 
  mutate(deep = cumsum(cumsum(str_detect(case, "[Uu]p") & !is.na(case))))
# A tibble: 18 x 3
# Groups:   ID [6]
#   ID    case   deep
#   <chr> <chr> <int>
# 1 aa    <NA>      0
# 2 aa    <NA>      0
# 3 aa    Up        1
# 4 aa    <NA>      2
# 5 cc    <NA>      0
# 6 cc    <NA>      0
# 7 dd    <NA>      0
# 8 dd    <NA>      0
# 9 dd    Up        1
#10 dd    <NA>      2
#11 dd    <NA>      3
#12 dd    <NA>      4
#13 ee    <NA>      0
#14 ee    <NA>      0
#15 ee    <NA>      0
#16 ff    up        1
#17 ff    <NA>      2
#18 gg    <NA>      0

数据

D1 <- structure(list(ID = c("aa", "aa", "aa", "aa", "cc", "cc", "dd", 
 "dd", "dd", "dd", "dd", "dd", "ee", "ee", "ee", "ff", "ff", "gg"
 ), case = c(NA, NA, "Up", NA, NA, NA, NA, NA, "Up", NA, NA, NA, 
 NA, NA, NA, "up", NA, NA)), class = "data.frame", row.names = c(NA, 
 -18L))

答案 1 :(得分:1)

这是data.table中的内容:

library(data.table)
setDT(D1)
D1[, 
   deep := {
     tmp <- grep("up", case, ignore.case = TRUE)[1]
     if (is.na(tmp)) rep(0L, .N) else c(rep(0L, tmp-1L), seq_len(.N - tmp + 1L))
   } , 
   by = ID]

      ID case deep
 1: aa <NA>    0
 2: aa <NA>    0
 3: aa   Up    1
 4: aa <NA>    2
 5: cc <NA>    0
 6: cc <NA>    0
 7: dd <NA>    0
 8: dd <NA>    0
 9: dd   Up    1
10: dd <NA>    2
11: dd <NA>    3
12: dd <NA>    4
13: ee <NA>    0
14: ee <NA>    0
15: ee <NA>    0
16: ff   up    1
17: ff <NA>    2
18: gg <NA>    0

数据

D1 <- data.frame(
  ID = c("aa", "aa", "aa", "aa", "cc", "cc", "dd", "dd", "dd", "dd", "dd", 
         "dd", "ee", "ee", "ee", "ff", "ff", "gg"), 
  case = c(NA, NA, "Up", NA, NA, NA, NA, NA, "Up", NA, NA, NA, NA, NA, NA, 
           "up", NA, NA) 
)