Генерируйте фрейм данных присутствия / отсутствия и подсчета, помеченный ежечасно по местоположению и идентификатору (все возможные комбинации) из данных вхождений с отметками времени в R - PullRequest
0 голосов
/ 22 октября 2019

У меня есть дата с метками времени, когда отдельное животное (ID) обнаруживается в определенных местах. Вот краткий пример данных (упорядоченный по местоположению, затем timestampUTC для ясности):

df <- read.table(text =
                   "timestampUTC    location    ID
                 '2017-10-11 04:57:16'  JB12    A69-1602-2429
                 '2017-10-11 04:58:25'  JB12    A69-1602-2429
                 '2017-10-11 04:59:08'  JB12    A69-1602-2429
                 '2017-10-11 05:00:01'  JB12    A69-1602-2429
                 '2017-10-11 05:03:04'  JB12    A69-1602-2429
                 '2017-10-11 05:04:38'  JB12    A69-1602-2429
                 '2017-10-11 04:56:20'  JB13    A69-1601-47280
                 '2017-10-11 04:57:44'  JB13    A69-1601-47280
                 '2017-10-11 04:59:00'  JB13    A69-1601-47280
                 '2017-10-11 04:59:56'  JB13    A69-1601-47280
                 '2017-10-11 05:01:16'  JB13    A69-1601-47280
                 '2017-10-11 05:02:20'  JB13    A69-1601-47280
                 '2017-10-11 05:02:56'  JB13    A69-1601-47280
                 '2017-10-11 05:03:34'  JB13    A69-1601-47280
                 '2017-10-11 05:08:29'  JB13    A69-1602-2429
                 '2017-10-11 04:56:43'  WBR A69-1602-2428
                 '2017-10-11 04:57:09'  WBR A69-1602-2425
                 '2017-10-11 04:58:11'  WBR A69-1602-2428
                 '2017-10-11 04:58:42'  WBR A69-1602-2425
                 '2017-10-11 04:59:34'  WBR A69-1602-2428
                 '2017-10-11 05:00:13'  WBR A69-1602-2425
                 '2017-10-11 05:00:47'  WBR A69-1602-2428
                 '2017-10-11 05:01:39'  WBR A69-1602-2428
                 '2017-10-11 05:01:43'  WBR A69-1602-2425
                 '2017-10-11 05:02:49'  WBR A69-1602-2428
                 '2017-10-11 05:03:36'  WBR A69-1602-2428
                 '2017-10-11 05:04:38'  WBR A69-1602-2428
                 '2017-10-11 05:07:32'  WBR A69-1602-2428", header = T)

Я хочу создать кадр данных из этих данных, где для каждого ежечасного бина и каждого местоположения и каждого идентификатора, который у меня есть,столбец с указанием того, присутствовал ли этот идентификатор (1) или отсутствовал (0) в этом месте в этот час, и столбец с количеством наблюдений для этого идентификатора в этом месте в этот час. В несколько иной формулировке - для каждого идентификатора я хочу знать, присутствует ли он (1) или отсутствует (0), а также количество наблюдений для каждого часового интервала периода исследования в каждом местоположении.

Например,приведенные выше данные имеют 4 уникальных идентификатора, 3 уникальных местоположения и наблюдения, которые попадают в две почасовые ячейки (2017-10-11 04:00:00, 2017-10-11 05:00:00). Результатом будет df с 24 строками (4 идентификатора x 3 местоположения x 2 почасовых ячейки). Вывод должен выглядеть примерно так:

output <- read.table(text =
                   "HourlyBinUTC    location    ID  count   present
                 '2017-10-11 04:00:00'  JB13    A69-1601-47280  4   1
                 '2017-10-11 04:00:00'  JB13    A69-1602-2429   0   0
                 '2017-10-11 04:00:00'  JB13    A69-1602-2428   0   0
                 '2017-10-11 04:00:00'  JB13    A69-1602-2425   0   0
                 '2017-10-11 04:00:00'  JB12    A69-1601-47280  0   0
                 '2017-10-11 04:00:00'  JB12    A69-1602-2429   4   1
                 '2017-10-11 04:00:00'  JB12    A69-1602-2428   0   0
                 '2017-10-11 04:00:00'  JB12    A69-1602-2425   0   0
                 '2017-10-11 04:00:00'  WBR A69-1601-47280  0   0
                 '2017-10-11 04:00:00'  WBR A69-1602-2429   0   0
                 '2017-10-11 04:00:00'  WBR A69-1602-2428   3   1
                 '2017-10-11 04:00:00'  WBR A69-1602-2425   2   1
                 '2017-10-11 05:00:00'  JB13    A69-1601-47280  4   1
                 '2017-10-11 05:00:00'  JB13    A69-1602-2429   1   1
                 '2017-10-11 05:00:00'  JB13    A69-1602-2428   0   0
                 '2017-10-11 05:00:00'  JB13    A69-1602-2425   0   0
                 '2017-10-11 05:00:00'  JB12    A69-1601-47280  0   0
                 '2017-10-11 05:00:00'  JB12    A69-1602-2429   3   1
                 '2017-10-11 05:00:00'  JB12    A69-1602-2428   0   0
                 '2017-10-11 05:00:00'  JB12    A69-1602-2425   0   0
                 '2017-10-11 05:00:00'  WBR A69-1601-47280  0   0
                 '2017-10-11 05:00:00'  WBR A69-1602-2429   0   0
                 '2017-10-11 05:00:00'  WBR A69-1602-2428   6   1
                 '2017-10-11 05:00:00'  WBR A69-1602-2425   2   1", header = T)

(в моем реальном df, который охватывает 19 887 часовых корзин с 17 индивидуумами и 4 местоположениями, я ожидаю, что на выходе будет 1 352 316 строк)

Я новичок в R и играл с reshape () и dcast (), но не достаточно знаком с аргументами, чтобы получить то, что мне нужно. Я подозреваю, что это будет работа для Tidyverse - которую я (ясно) отчаянно должен изучить!

Заранее спасибо!

1 Ответ

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

Вам не нужны никакие пакеты для этого. Я прочитал в вашем df, но установил опцию stringsAsFactors.

df <- read.table(text =
                 "timestampUTC    location    ID
                 '2017-10-11 04:57:16'  JB12    A69-1602-2429
                 ## ...
                 '2017-10-11 05:07:32'  WBR A69-1602-2428",
                 header = TRUE, stringsAsFactors = FALSE)

Теперь скажите R, что первый столбец является меткой времени, а затем округлите метку времени.

df[["timestampUTC"]] <- as.POSIXct(df[["timestampUTC"]], tz = "UTC")
df[["timestampUTC"]] <- trunc(df[["timestampUTC"]], "hours")

Затем вызовите table и преобразуйте результат в фрейм данных.

result <- as.data.frame(table(df))

##           timestampUTC location             ID Freq
## 1  2017-10-11 04:00:00     JB12 A69-1601-47280    0
## 2  2017-10-11 05:00:00     JB12 A69-1601-47280    0
## 3  2017-10-11 04:00:00     JB13 A69-1601-47280    4
## 4  2017-10-11 05:00:00     JB13 A69-1601-47280    4
## 5  2017-10-11 04:00:00      WBR A69-1601-47280    0
## 6  2017-10-11 05:00:00      WBR A69-1601-47280    0
## 7  2017-10-11 04:00:00     JB12  A69-1602-2425    0
## 8  2017-10-11 05:00:00     JB12  A69-1602-2425    0
## 9  2017-10-11 04:00:00     JB13  A69-1602-2425    0
## 10 2017-10-11 05:00:00     JB13  A69-1602-2425    0
## 11 2017-10-11 04:00:00      WBR  A69-1602-2425    2
## 12 2017-10-11 05:00:00      WBR  A69-1602-2425    2
## 13 2017-10-11 04:00:00     JB12  A69-1602-2428    0
## 14 2017-10-11 05:00:00     JB12  A69-1602-2428    0
## 15 2017-10-11 04:00:00     JB13  A69-1602-2428    0
## 16 2017-10-11 05:00:00     JB13  A69-1602-2428    0
## 17 2017-10-11 04:00:00      WBR  A69-1602-2428    3
## 18 2017-10-11 05:00:00      WBR  A69-1602-2428    6
## 19 2017-10-11 04:00:00     JB12  A69-1602-2429    3
## 20 2017-10-11 05:00:00     JB12  A69-1602-2429    3
## 21 2017-10-11 04:00:00     JB13  A69-1602-2429    0
## 22 2017-10-11 05:00:00     JB13  A69-1602-2429    1
## 23 2017-10-11 04:00:00      WBR  A69-1602-2429    0
## 24 2017-10-11 05:00:00      WBR  A69-1602-2429    0

Если вы хотите включить ID, скажем, который никогда не появлялся в данных, вам нужно сказать table какие значения для ID возможны. Вы можете сделать это, задав ID фактор.

df[["ID"]] <- factor(df[["ID"]],
                     levels = c("A69-1602-2429", "A69-1601-47280",
                                "A69-1602-2428", "A69-1602-2425",
                                "foo"))

Или для дополнительных часов:

df[["timestampUTC"]] <-
    factor(df[["timestampUTC"]],
           levels =
               seq(from = as.POSIXct("2017-10-01 00:00:00", tz = "UTC"),
                   to   = as.POSIXct("2017-10-03 00:00:00", tz = "UTC"),
                   by   = "1 hour"))

Результаты будут включать нулевые отсчеты.

## ...
## 25 2017-10-11 04:00:00     JB12            foo    0
## 26 2017-10-11 05:00:00     JB12            foo    0
## 27 2017-10-11 04:00:00     JB13            foo    0
## 28 2017-10-11 05:00:00     JB13            foo    0
## 29 2017-10-11 04:00:00      WBR            foo    0
## 30 2017-10-11 05:00:00      WBR            foo    0

Вместо переменной ноль-один для present я бы предложил логический вектор:

present <- result$Freq > 0
cbind(result, present)

##           timestampUTC location             ID Freq present
## 1  2017-10-11 04:00:00     JB12 A69-1601-47280    0   FALSE
## 2  2017-10-11 05:00:00     JB12 A69-1601-47280    0   FALSE
## 3  2017-10-11 04:00:00     JB13 A69-1601-47280    4    TRUE
## 4  2017-10-11 05:00:00     JB13 A69-1601-47280    4    TRUE
## 5  2017-10-11 04:00:00      WBR A69-1601-47280    0   FALSE
## ...
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...