Home > OS >  How to adding row based on the information of first row of each group in R
How to adding row based on the information of first row of each group in R

Time:07-20

I hope you are doing well. I have a question how we add value for last row in group to last row because I have 5000 row of this. Thank you.

Here is the dataset

ID, Value
1, 1
1, 2
1, 3
1, 4
2, 5
2, 6 
2, 7
2, 8

and the result should be as follows

ID, Value
    1, 1
    1, 2
    1, 3
    1, 4
    1, 1
    2, 5
    2, 6 
    2, 7
    2, 8
    2, 5

Thank you in advance for your help

CodePudding user response:

Here is a base R method:

do.call(rbind, 
    lapply(split(dat, dat$ID), \(id_df) rbind(id_df, id_df[1,]))
) 
#      ID Value
# 1.1   1     1
# 1.2   1     2
# 1.3   1     3
# 1.4   1     4
# 1.5   1     1
# 2.5   2     5
# 2.6   2     6
# 2.7   2     7
# 2.8   2     8
# 2.51  2     5

It does give you slightly strange row names - if you care about that you can wrap it in (or pipe it to) tibble::as_tibble(), which removes row names altogether.

Alternatively you could do data.table::rbindlist(lapply(split(dat, dat$ID), \(id_df) rbind(id_df, id_df[1,]))), becausedata.table also does not use row names.

Data

dat  <- read.csv(text = "ID, Value
1, 1
1, 2
1, 3
1, 4
2, 5
2, 6 
2, 7
2, 8", h=T)

CodePudding user response:

Within tidyverse, you could use add_row with do (or the experimental group_modify):

dat |>
  group_by(ID) |>
  do(add_row(., ID = unique(.$ID), Value = first(.$Value))) |>
  ungroup()
dat |>
  group_by(ID) |>
  group_modify(~ add_row(., Value = first(.$Value))) |>
  ungroup()

Output:

# A tibble: 10 × 2
      ID Value
   <int> <dbl>
 1     1     1
 2     1     2
 3     1     3
 4     1     4
 5     1     1
 6     2     5
 7     2     6
 8     2     7
 9     2     8
10     2     5

Thanks to @SamR for the data.

  • Related