Oliver
Oliver

Reputation: 443

How can I split non consecutive numbers in different lists

I have the following list of numeric values in R:

sales_by_hour = c(130, 21, 0, 0, 0, 0, 6, 244, 391, 408, 431, 0, 0, 471, 
                  530, 573, 643, 643, 667, 787, 990, 1024, 1012, 712)

Then I have applied the following code to obtain the indexes of the min values

which(test2==0)

which returns the values c(3,4,5,6,12,13). However I would like to then split again this list in 2 or more lists ex. c(3,4,5,6) and c(12,13), since I want to separate non consecutive series of number.

Upvotes: 3

Views: 589

Answers (2)

G. Grothendieck
G. Grothendieck

Reputation: 269634

1) rleid Using the input in the Note at the end, we can use rleid from data.table. It assigns a unique number to each run in the input resulting in a compact solution.

library(data.table)
split(seq_along(x)[x == 0], rleid(x)[x == 0])

giving:

$`3`
[1] 3 4 5 6

$`9`
[1] 12 13

2) Base R This could also be done in base at the expense of a slightly longer solution. Here the value of inverse.rle(r) is the same as the value of rleid(x) and is done without using any packages.

r <- rle(x)
r$values <- seq_along(r$values)
split(seq_along(x)[x == 0], inverse.rle(r)[x == 0])

Note

The input in reproducible form:

Line <- "130   21    0    0    0    0    6  244  391  408  431  0  0  471  530  573  643  643  667  787  990 1024 1012  712"
x <- scan(text = Line)

Upvotes: 1

M--
M--

Reputation: 28850

It can be done in base:

split(which(sales_by_hour==0), cumsum(c(1, diff(which(sales_by_hour==0)) != 1)))

#> $`1`
#> [1] 3 4 5 6
#> 
#> $`2`
#> [1] 12 13

Upvotes: 3

Related Questions