0

I am working with a list as follows:

  > l <- list(c(2,4,9), c(4,2,6,1))
  > m <- melt(l)
  > m 
  value L1
      2  1
      4  1
      9  1
      4  2
      2  2
      6  2
      1  2

i want to add index i for my resulting data frame m looks like this:

> m
i  value L1
1     2  1
2     4  1
3     9  1
1     4  2
2     2  2
3     6  2
4     1  2

i indicating 3 values belongs to first list element and 4 values belongs to the second list element.

How can i archive it please, can anyone help?

aliocee
  • 730
  • 9
  • 25

3 Answers3

2

You could use splitstackshape

library(splitstackshape)
getanID(m, 'L1')[]
#   value L1 .id
#1:     2  1   1
#2:     4  1   2
#3:     9  1   3
#4:     4  2   1
#5:     2  2   2
#6:     6  2   3
#7:     1  2   4

Or using base R

transform(stack(setNames(l, seq_along(l))), .id= rapply(l, seq_along))
akrun
  • 874,273
  • 37
  • 540
  • 662
2

Just for completeness, some other options

data.table (which is basically what getanID is doing)

library(data.table)
setDT(m)[, i := seq_len(.N), L1]

dplyr

library(dplyr)
m %>%
  group_by(L1) %>%
  mutate(i = row_number())

Base R (from comments by @user20650)

transform(m, i = ave(L1, L1, FUN = seq_along)) 
David Arenburg
  • 91,361
  • 17
  • 137
  • 196
1

Less elegant than ave but does the work:

transform(m, i=unlist(sapply(rle(m$L1)$length, seq_len)))
#  value L1 i
#1     2  1 1
#2     4  1 2
#3     9  1 3
#4     4  2 1
#5     2  2 2
#6     6  2 3
#7     1  2 4

Or

 m$i <- sequence(rle(m$L1)$lengths)
akrun
  • 874,273
  • 37
  • 540
  • 662
Colonel Beauvel
  • 30,423
  • 11
  • 47
  • 87