Как назначить уровни для столбца на основе определенных дат и уровней в другом столбце? - PullRequest
1 голос
/ 24 октября 2019

У меня есть пример набора данных с 3 столбцами: JulianDay, Device и location. См. Код ниже.

structure(list(JulianDay = 40:69, Device = structure(c(1L, 2L, 
3L, 1L, 2L, 3L, 1L, 2L, 3L, 2L, 3L, 1L, 2L, 3L, 1L, 2L, 3L, 1L, 
2L, 3L, 1L, 3L, 1L, 2L, 3L, 1L, 2L, 3L, 1L, 2L), .Label = c("a", 
"b", "c"), class = "factor"), Location = c(1, 2, 3, 1, 2, 3, 
1, 2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3, 
1, 2, 3)), class = "data.frame", row.names = c(NA, -30L))

Просматривая данные, вы можете видеть, что Устройство a находится в местоположении 1 в дни 40, 43, 46. Однако устройства меняют местоположения, и местоположение 1 занято устройством bв дни 49, 52, 55 и устройство c на 61, 64, 67. Подобные изменения происходят для всех трех устройств.

Теперь представьте, что у нас есть только первые два столбца, но я знаю каждую дату, когда устройствоменяет локации и в какую локацию идет. Как я могу восстановить колонку 3 с этой информацией. Очевидно, что с 30 строками было бы легко просто ввести вручную, но я имею дело с реальным кадром данных, который имеет несколько сотен тысяч строк.

РЕДАКТИРОВАТЬ:

structure(list(JulianDay = c(40, 40, 40, 41, 41, 41, 42, 42, 
42, 43, 43, 43, 44, 44, 44, 45, 45, 45), Device = structure(c(1L, 
2L, 3L, 1L, 2L, 3L, 2L, 3L, 1L, 2L, 3L, 1L, 3L, 1L, 2L, 3L, 1L, 
2L), .Label = c("a", "b", "c"), class = "factor"), Location = c(1, 
2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3)), class = "data.frame", row.names = c(NA, 
-18L))

Вотаналогичные данные, которые могут прояснить вопрос. Каждое устройство активно каждый день, и на каждый день есть 3 местоположения. Без физического столбца Location (но зная, что должно содержаться внутри), я хотел бы закодировать что-то вроде следующего:

if(JulianDay < 41 & Device == 'A') { Location == 1}
if(JulianDay > 41 * JulianDay < 44 & Device == 'A') { Location == 3}
if(JulianDay > 44 & Device == 'A') {Location == 2

Так, чтобы был заполнен третий столбец (Location).

1 Ответ

1 голос
/ 24 октября 2019

Если у вас есть набор условных ожиданий, основанных на JulianDay и Device, которые необходимо выполнить по очереди для создания Location, то вам следует взглянуть на dplyr::case_when.

Документы (см. ?dplyr::case_when):

Эта функция позволяет векторизовать несколько операторов if_else (). Это эквивалент R оператора SQL «CASE WHEN». Если не найдено ни одного случая, возвращается «NA».

Например, в вашем примере,

data <- structure(list(JulianDay = c(40, 40, 40, 41, 41, 41, 42, 42, 
42, 43, 43, 43, 44, 44, 44, 45, 45, 45), Device = structure(c(1L, 
2L, 3L, 1L, 2L, 3L, 2L, 3L, 1L, 2L, 3L, 1L, 3L, 1L, 2L, 3L, 1L, 
2L), .Label = c("a", "b", "c"), class = "factor"), Location = c(1, 
2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3)), class = "data.frame", row.names = c(NA, 
-18L))

library(dplyr)

data$Location <- case_when(
  data$JulianDay < 41 & data$Device == "a" ~ 1,
  data$JulianDay > 41 & data$JulianDay < 44 & data$Device == "a" ~ 3,
  data$JulianDay > 44 & data$Device == "a" ~ 2
)
...