R: вычислить линейную регрессию и получить наклон для «подмножества данных»

#r #dataframe #dplyr

#r #dataframe #dplyr

Вопрос:

Моя цель — выяснить период полураспада (от терминальной фазы, если кто-нибудь знаком с фармакокинетикой)

У меня есть некоторые данные, содержащие следующее;

1500 строк, с ID основным «ключом». В каждом есть 15 строк ID . Тогда у меня есть другие столбцы TIME и CONCENTRATION . Теперь то, что я хочу сделать, это для каждого ID удалить первый TIME (который равен «000» (числовой)), затем запустить lm() function для оставшихся 14 строк для каждого ID , а затем использовать abs() для извлечения абсолютного значения наклона, а затем сохранить это в новом столбце с именем THALF . (Если кто-нибудь знаком с фармакокинетикой, может быть, есть лучший способ сделать это?)

Но я не смог этого сделать, используя свои ограниченные знания R.

Вот что я придумал до сих пор:

 data_new <- data %>% dplyr::group_by(data $ID) %>% dplyr::filter(data $TIME != 10) %>% dplyr::mutate(THAFL = abs(lm$coefficients[2](data $CONC ~ data $TIME)))
 

Из того, что я понял из других ответов Stackoverflow, lm $ коэффициенты [2] извлекут наклон.

Но, однако, я не смог заставить это работать. Я получаю эту ошибку при попытке запустить код:

 Error: Problem with `mutate()` input `..1`.
x Input `..1` can't be recycled to size 15.
i Input `..1` is `data$ID`.
i Input `..1` must be size 15 or 1, not 1500.
i The error occurred in group 1: data$ID = "pat1".
 

Любые предложения о том, как это решить? ЕСЛИ вам нужна дополнительная информация, дайте мне знать, пожалуйста.

(Кроме того, если кто-нибудь знаком с фармакокинетикой, когда они запрашивают период полураспада из терминальной фазы, делаю ли я lm () из максимальной концентрации? У меня есть столбец со значением для самой высокой наблюдаемой концентрации в какое время.)

Комментарии:

1. Привет, Карлтон, возможно ли поделиться образцом данных, возможно, используя dput(head(yourdata,100)) ?

2. Кроме того, не указывайте data$ внутри операторов dplyr, в этом нет необходимости

3. @Duck Хорошо, я это сделал. В разделе редактирование.

4. Я не думаю, что там достаточно данных, чтобы вы могли что-то попробовать. Вам нужны все данные? @Duck

5. В вашем примере данных TIME всегда 10, что означает, что каждая строка исключается. Может быть, вы можете разделить все строки на несколько отдельных ID s, скажем, три или четыре

Ответ №1:

Если после подгонки модели вам все еще нужны наблюдения TIME == 10 , вы можете попробовать суммировать после группировки по ID , а затем использовать правое соединение

 data %>% 
  filter(TIME != 10) %>% 
  group_by(ID) %>%
  summarise(THAFL = abs(lm(CONC ~ TIME)$coefficients[2])) %>% 
  right_join(data, by = "ID")


# A tibble: 30 x 16
   ID      THAFL Sex   Weight..kg. Height..cm. Age..yrs. T134A A443G G769C G955C A990C  TIME  CONC LBM   `data_combine$ID`  CMAX
   <chr>   <dbl> <chr>       <int>       <int>     <int> <int> <int> <int> <int> <int> <dbl> <dbl> <chr> <chr>             <dbl>
 1 pat1  0.00975 F              50         135        47     0     2     1     2     0    10  0    Under pat1                 60
 2 pat1  0.00975 F              50         135        47     0     2     1     2     0    20  6.93 Under pat1                 60
 3 pat1  0.00975 F              50         135        47     0     2     1     2     0    30 12.2  Under pat1                 60
 4 pat1  0.00975 F              50         135        47     0     2     1     2     0    45 14.8  Under pat1                 60
 5 pat1  0.00975 F              50         135        47     0     2     1     2     0    60 15.0  Under pat1                 60
 6 pat1  0.00975 F              50         135        47     0     2     1     2     0    90 12.4  Under pat1                 60
 7 pat1  0.00975 F              50         135        47     0     2     1     2     0   120  9.00 Under pat1                 60
 8 pat1  0.00975 F              50         135        47     0     2     1     2     0   150  6.22 Under pat1                 60
 9 pat1  0.00975 F              50         135        47     0     2     1     2     0   180  4.18 Under pat1                 60
10 pat1  0.00975 F              50         135        47     0     2     1     2     0   240  1.82 Under pat1                 60
# ... with 20 more rows
 

Если после подгонки модели вы не хотите, чтобы строки с TIME == 10 отображались в вашем наборе данных, вы можете использовать mutate

 data %>% 
  filter(TIME != 10) %>% 
  group_by(ID) %>%
  mutate(THAFL = abs(lm(CONC ~ TIME)$coefficients[2]))

# A tibble: 28 x 16
# Groups:   ID [2]
   ID    Sex   Weight..kg. Height..cm. Age..yrs. T134A A443G G769C G955C A990C  TIME  CONC LBM   `data_combine$ID`  CMAX   THAFL
   <chr> <chr>       <int>       <int>     <int> <int> <int> <int> <int> <int> <dbl> <dbl> <chr> <chr>             <dbl>   <dbl>
 1 pat1  F              50         135        47     0     2     1     2     0    20  6.93 Under pat1                 60 0.00975
 2 pat2  M              75         175        29     0     2     0     0     0    20  6.78 Under pat2                 60 0.00835
 3 pat1  F              50         135        47     0     2     1     2     0    30 12.2  Under pat1                 60 0.00975
 4 pat2  M              75         175        29     0     2     0     0     0    30 11.6  Above pat2                 60 0.00835
 5 pat1  F              50         135        47     0     2     1     2     0    45 14.8  Under pat1                 60 0.00975
 6 pat2  M              75         175        29     0     2     0     0     0    45 13.5  Under pat2                 60 0.00835
 7 pat1  F              50         135        47     0     2     1     2     0    60 15.0  Under pat1                 60 0.00975
 8 pat2  M              75         175        29     0     2     0     0     0    60 13.1  Above pat2                 60 0.00835
 9 pat1  F              50         135        47     0     2     1     2     0    90 12.4  Under pat1                 60 0.00975
10 pat2  M              75         175        29     0     2     0     0     0    90  9.77 Under pat2                 60 0.00835
# ... with 18 more rows
 

Комментарии:

1. Спасибо за ваш ответ! Если мне нужно дополнительно отфильтровать только строки, где TIME> = CMAX, добавить ли мне дополнительную функцию filter () или сделать это в том же filter (), который у меня уже есть?

2. Вы можете сделать это в том же filter операторе: filter(TIME != 10 amp; TIME >= CMAX)

Ответ №2:

Вы можете использовать broom :

 library(broom)
library(dplyr)
#Code
data %>% group_by(ID) %>%
  filter(TIME!=10) %>%
  do(fit = tidy(lm(CONC ~ TIME, data = .))) %>% 
  unnest(fit) %>%
  filter(term=='TIME') %>%
  mutate(estimate=abs(estimate))
 

Вывод:

 # A tibble: 2 x 6
  ID    term  estimate std.error statistic p.value
  <chr> <chr>    <dbl>     <dbl>     <dbl>   <dbl>
1 pat1  TIME   0.00975   0.00334     -2.92  0.0128
2 pat2  TIME   0.00835   0.00313     -2.67  0.0204
 

Если требуется объединение с исходными данными, попробуйте:

 #Code 2
data <- data %>% left_join(data %>% group_by(ID) %>%
  filter(TIME!=10) %>%
  do(fit = tidy(lm(CONC ~ TIME, data = .))) %>% 
  unnest(fit) %>%
  filter(term=='TIME') %>%
  mutate(estimate=abs(estimate)) %>%
  select(c(ID,estimate)))
 

Аналогично @RicS.

Комментарии:

1. Спасибо за ваш ответ! Если мне нужно дополнительно отфильтровать только строки, где TIME> = CMAX, добавить ли мне дополнительную функцию filter () или сделать это в том же filter (), который у меня уже есть?

2. @Carlton Вы можете добавить еще один filter(), потому что, если вы добавите в первое, оба условия будут оцениваться совместно. Вы могли бы сделать filter(TIME!=10|TIME >= CMAX) это только в одной строке!

3. @Carlton Также filter(TIME!=10,TIME >= CMAX) оценит оба условия совместно!

4. Еще раз спасибо за помощь! Очень полезно! Я проголосовал, но я должен принять другой ответ, извините, он ответил первым. Извиняюсь за это и благодарю вас за помощь!