Пакет Broom - Ошибка в lm.fit (x, y, offset = offset, singular.ok = singular.ok,): 0 (не NA) случаев

У меня есть фреймворк с атрибутами учащихся и результатами тестов, и я пытаюсь подогнать линейную модель для каждого уровня обучения (с 1 по 12). Я использую пакет broom для эффективного создания модели для каждого класса. Ниже приведен упрощенный пример набора данных и код, который я использую.

#start df creation 

grade <- rep(1:12, each = 40)
attendance_rate <- round(runif(480, min=25, max=100), 1)
test_growth <- round(runif(480, min = -12, max = 38))
binary_flag <- round(runif(480, min = 0, max = 1))
score <- round(runif(480, min = 92, max = 370))
survey_response <- round(runif(480, min = 1, max = 4))

df <- data.frame(grade, attendance_rate, test_growth, binary_flag, score, survey_response) 

df$survey_response[df$grade == 1] <- NA

# end df creation

#create train test split for each grade level
set.seed(123)

df_train <- lapply(split(seq(1:nrow(df)), df$grade), function(x) sample(x, floor(.6*length(x))))
df_test <- mapply(function(x,y) setdiff(x,y), x = split(seq(1:nrow(df)), df$grade), y = df_train)

df_train <- df[unlist(df_train),]

df_test <- df[unlist(df_test),]



#create models
models_nested <- df_train %>%
  group_by(grade) %>% nest() %>% 
  mutate(
    fit = map(data, ~ lm(score ~ attendance_rate + test_growth + binary_flag + survey_response, data = .x)),
    tidied = map(fit, tidy),
    augmented = map(fit, augment),
    glanced = map(fit, glance)
  )

К сожалению, когда я пытаюсь запустить блок кода, который начинается с models_nested, я получаю следующую ошибку:

Error in lm.fit(x, y, offset = offset, singular.ok = singular.ok, ...) : 
  0 (non-NA) cases

Я знаю, что это происходит, потому что все ученики 1-го класса имеют значение NA в столбце survey_response. Я не знаю, как решить эту проблему без запуска отдельной регрессии для 1-го класса, при которой столбец / переменная ответа на опрос полностью удаляется. Есть ли способ указать функции lm просто игнорировать переменную, если это конкретное подмножество оценок содержит только нулевые значения? Я, очевидно, хочу сохранить эту переменную в регрессии для других моделей уровня обучения.

Я постарался прояснить этот вопрос, но при необходимости буду рад уточнить в комментариях.

ИЗМЕНИТЬ 6/9/2020: я не хочу возвращать NA для модели первого класса, я просто хочу, чтобы линейная модель для первого класса запускалась без столбца survey_response. Я бы хотел, чтобы столбец survey_response был включен во все другие модели уровня обучения.

Я надеюсь, что кто-то может помочь!


person rachael_learns    schedule 09.06.2020    source источник


Ответы (2)


Мы можем проверить NA значения в survey_response и соответственно использовать модель.

library(broom)
library(dplyr)
library(tidyr)
library(purrr)

df_train %>%
   group_by(grade) %>% 
   nest() %>% 
    mutate(fit = map(data, ~ if(all(is.na(.x$survey_response)))
              lm(score ~ attendance_rate + test_growth + binary_flag, data = .x) 
              else lm(score ~ attendance_rate + test_growth + binary_flag + survey_response, data = .x)),
        tidied = map(fit, tidy),
        augmented = map(fit, augment),
        glanced = map(fit, glance))


#   grade data              fit    tidied           augmented          glanced          
#   <int> <list>            <list> <list>           <list>             <list>           
# 1     1 <tibble [24 × 5]> <lm>   <tibble [4 × 5]> <tibble [24 × 11]> <tibble [1 × 11]>
# 2     2 <tibble [24 × 5]> <lm>   <tibble [4 × 5]> <tibble [24 × 11]> <tibble [1 × 11]>
# 3     3 <tibble [24 × 5]> <lm>   <tibble [4 × 5]> <tibble [24 × 11]> <tibble [1 × 11]>
# 4     4 <tibble [24 × 5]> <lm>   <tibble [4 × 5]> <tibble [24 × 11]> <tibble [1 × 11]>
# 5     5 <tibble [24 × 5]> <lm>   <tibble [4 × 5]> <tibble [24 × 11]> <tibble [1 × 11]>
# 6     6 <tibble [24 × 5]> <lm>   <tibble [4 × 5]> <tibble [24 × 11]> <tibble [1 × 11]>
# 7     7 <tibble [24 × 5]> <lm>   <tibble [4 × 5]> <tibble [24 × 11]> <tibble [1 × 11]>
# 8     8 <tibble [24 × 5]> <lm>   <tibble [4 × 5]> <tibble [24 × 11]> <tibble [1 × 11]>
# 9     9 <tibble [24 × 5]> <lm>   <tibble [4 × 5]> <tibble [24 × 11]> <tibble [1 × 11]>
#10    10 <tibble [24 × 5]> <lm>   <tibble [4 × 5]> <tibble [24 × 11]> <tibble [1 × 11]>
#11    11 <tibble [24 × 5]> <lm>   <tibble [4 × 5]> <tibble [24 × 11]> <tibble [1 × 11]>
#12    12 <tibble [24 × 5]> <lm>   <tibble [4 × 5]> <tibble [24 × 11]> <tibble [1 × 11]>
person Ronak Shah    schedule 09.06.2020
comment
Спасибо тебе за это. Я понял, что мог бы сделать свой вопрос более ясным, и прошу прощения. Я не хочу просто возвращать NA для 1-го класса, я хотел бы запустить альтернативную линейную модель, которая не включает столбец ответов на опрос. Поэтому я бы хотел, чтобы следующая модель работала только для первого класса: lm (score ~ ​​посещаемость_rate + test_growth + binary_flag, data = .x) Обратите внимание, что переменная survey_response удалена, но опять же только для первого класса. Это возможно? Еще раз спасибо за ваше время и вклад. - person rachael_learns; 09.06.2020
comment
@rachael_learns Но не всегда это только survey_response. выдаст вам ошибку. Иногда test_growth также выдает ошибку, верно? Как вы это узнаете? - person Ronak Shah; 09.06.2020
comment
Причиной проблемы всегда является survey_response - я работаю с данными об образовании, и это просто особенность этого конкретного набора данных, что дети в первом классе не проходят этот опрос, в то время как все другие классы принимают участие в опросе. - person rachael_learns; 09.06.2020
comment
ДА ЭТО РАБОТАЕТ !! СПАСИБО БОЛЬШОЕ. Я надеюсь, что однажды я буду так же хорош в R! : D - person rachael_learns; 09.06.2020

Мы можем использовать possibly из purrr

library(broom)
library(dplyr)
library(tidyr)
library(purrr)

poslm <- possibly(lm, otherwise = NA)
df_train %>%
   group_by(grade) %>% 
   nest() %>% 
   mutate(fit = map(data, ~ poslm(score ~ attendance_rate + test_growth + 
              binary_flag + survey_response, data = .x)), 
         tidied = map(fit, possibly(tidy, otherwise = NA)),
            augmented = map(fit, possibly(augment, otherwise = NA)),
          glanced = map(fit, possibly(glance, otherwise = NA)))
# A tibble: 12 x 6
# Groups:   grade [12]
#   grade data              fit       tidied           augmented          glanced          
#   <int> <list>            <list>    <list>           <list>             <list>           
# 1     1 <tibble [24 × 5]> <lgl [1]> <lgl [1]>        <lgl [1]>          <lgl [1]>        
# 2     2 <tibble [24 × 5]> <lm>      <tibble [5 × 5]> <tibble [24 × 12]> <tibble [1 × 11]>
# 3     3 <tibble [24 × 5]> <lm>      <tibble [5 × 5]> <tibble [24 × 12]> <tibble [1 × 11]>
# 4     4 <tibble [24 × 5]> <lm>      <tibble [5 × 5]> <tibble [24 × 12]> <tibble [1 × 11]>
# 5     5 <tibble [24 × 5]> <lm>      <tibble [5 × 5]> <tibble [24 × 12]> <tibble [1 × 11]>
# 6     6 <tibble [24 × 5]> <lm>      <tibble [5 × 5]> <tibble [24 × 12]> <tibble [1 × 11]>
# 7     7 <tibble [24 × 5]> <lm>      <tibble [5 × 5]> <tibble [24 × 12]> <tibble [1 × 11]>
# 8     8 <tibble [24 × 5]> <lm>      <tibble [5 × 5]> <tibble [24 × 12]> <tibble [1 × 11]>
# 9     9 <tibble [24 × 5]> <lm>      <tibble [5 × 5]> <tibble [24 × 12]> <tibble [1 × 11]>
#10    10 <tibble [24 × 5]> <lm>      <tibble [5 × 5]> <tibble [24 × 12]> <tibble [1 × 11]>
#11    11 <tibble [24 × 5]> <lm>      <tibble [5 × 5]> <tibble [24 × 12]> <tibble [1 × 11]>
#12    12 <tibble [24 × 5]> <lm>      <tibble [5 × 5]> <tibble [24 × 12]> <tibble [1 × 11]>
person akrun    schedule 09.06.2020
comment
Спасибо за ответ. Я понимаю, что моему вопросу не хватало ясности. Я не хочу возвращать NA для модели первого класса, я просто хочу, чтобы линейная модель для первого класса работала без столбца survey_response. Я бы хотел, чтобы столбец survey_response был включен во все другие модели уровня обучения. Это возможно? - person rachael_learns; 09.06.2020