Проблема с sample_n (2, replace = F) в списке данных с размером некоторых данных менее 2 - PullRequest
0 голосов
/ 23 мая 2019

Мне нужна помощь с sample_n () в «dplyr» в R: У меня есть список данных riskset[[1]], riskset[[2]],..., riskset[[1000]]), каждый элемент riskset[[i]] списка представляет собой фрейм данных наблюдений, и я разделил наблюдения в каждом riskset на группу 1: 4 на основе распределения переменной. Таким образом, данные в riskset[[i]] выглядят так:

id      sex        grp      ...
1        F          1       ...
2        M          3       ...
3        F          1       ...
4        M          4       ...
5        F          2       ...
6        F          3       ...
......................

Я хочу взять 2 наблюдения из каждой группы в каждом наборе рисков и сохранить их как список выборки. я использовал sample<- list()

for(i in 1:1000){
sample[[i]] <- riskset[[i]] %>% group_by(grp) %>% sample_n(2,replace=F)
}

Это дало мне ошибку:

size must be less or equal than 1 (size of data), set ‘replace = TRUE’ to use sampling with replacement.

Я попробовал код на группе риска, который имеет более 2 объектов в каждой группе, это сработало. Но он не работает с набором рисков, у которого в некоторой группе менее 2 человек. Для группы, у которой есть менее 2 аксов, я хочу, чтобы у нее были все. И для группы, которая имеет более 2 акций, я хочу попробовать 2 акса без замены. Как я могу достичь своей цели выборки, используя функции R? Заранее спасибо!

1 Ответ

0 голосов
/ 23 мая 2019

Мы можем использовать map, чтобы зациклить list ('riskset'), затем сгруппировать по 'grp', применить sample_n

library(tidyerse)
out <- map(riskset, ~ .x  %>%
                    group_by(grp) %>%
                    sample_n(pmin(n(), 2), replace = TRUE))

Или другой вариант slice

map(riskset, ~ .x %>%
                  group_by(grp) %>%
                  slice(if(n() < 2) 1 else sample(row_number(), 2))

Или без использования if/else

map(riskset, ~ .x %>%
                  group_by(grp) %>%
                  slice(sample(seq_len(pmin(n(), 2)))))

данные

iris1 <-  iris %>%
               select(grp = Species, everything()) %>%
               slice(c(1:5, 51))
riskset <- list(iris1, iris1)
...