我有一个时间序列很多的数据框:
1 0:03 B 1
2 0:05 A 1
3 0:05 A 1
4 0:05 B 1
5 0:10 A 1
6 0:10 B 1
7 0:14 B 1
8 0:18 A 1
9 0:20 A 1
10 0:23 B 1
11 0:30 A 1
我想将时间序列每6分钟分组一次,并计算A和B的频率:
1 0:06 A 2
2 0:06 B 2
3 0:12 A 1
4 0:12 B 1
5 0:18 A 1
6 0:24 A 1
7 0:24 B 1
8 0:18 A 1
9 0:30 A 1
此外,时间序列的类别是字符。我该怎么办?
答案 0 :(得分:2)
POSIXct
,cut
的时间间隔为6分钟,然后是count
的方法。首先,您需要指定数据的年,月,日,小时,分钟和秒。这将有助于将其缩放到更大的数据集。
library(tidyverse)
library(lubridate)
# sample data
d <- data.frame(t = paste0("2019-06-02 ",
c("0:03","0:06","0:09","0:12","0:15",
"0:18","0:21","0:24","0:27","0:30"),
":00"),
g = c("A","A","B","B","B"))
d$t <- ymd_hms(d$t) # convert to POSIXct with `lubridate::ymd_hms()`
如果选中新日期列的class
,您将看到它是“ POSIXct”。
> class(d$t)
[1] "POSIXct" "POSIXt"
现在数据位于“ POSIXct”中,您可以每隔cut
分钟间隔!我们会将这个新的分组因子添加到名为tc
的新列中。
d$tc <- cut(d$t, breaks = "6 min")
d
t g tc
1 2019-06-02 00:03:00 A 2019-06-02 00:03:00
2 2019-06-02 00:06:00 A 2019-06-02 00:03:00
3 2019-06-02 00:09:00 B 2019-06-02 00:09:00
4 2019-06-02 00:12:00 B 2019-06-02 00:09:00
5 2019-06-02 00:15:00 B 2019-06-02 00:15:00
6 2019-06-02 00:18:00 A 2019-06-02 00:15:00
7 2019-06-02 00:21:00 A 2019-06-02 00:21:00
8 2019-06-02 00:24:00 B 2019-06-02 00:21:00
9 2019-06-02 00:27:00 B 2019-06-02 00:27:00
10 2019-06-02 00:30:00 B 2019-06-02 00:27:00
现在,您可以group_by
这个新的间隔(tc
)和您的分组列(g
),并计算发生的频率。获取组中观察的频率是相当普遍的操作,因此dplyr
为此提供了count
:
count(d, g, tc)
# A tibble: 7 x 3
g tc n
<fct> <fct> <int>
1 A 2019-06-02 00:03:00 2
2 A 2019-06-02 00:15:00 1
3 A 2019-06-02 00:21:00 1
4 B 2019-06-02 00:09:00 2
5 B 2019-06-02 00:15:00 1
6 B 2019-06-02 00:21:00 1
7 B 2019-06-02 00:27:00 2
如果您在控制台中运行?dplyr::count()
,则会看到count(d, tc)
只是group_by(d, g, tc) %>% summarise(n = n())
的包装。
答案 1 :(得分:0)
根据样本数据集,时间序列以一天中的时间给出,即没有日期。
data.table
程序包具有ITime
类,它是一天中的时间类,存储为一天中的整数秒数。使用data.table
,我们可以使用滚动连接将时间映射到6分钟间隔(右封闭间隔)的上限:
library(data.table)
# coerce from character to class ITime
setDT(ts)[, time := as.ITime(time)]
# create sequence of breaks
breaks <- as.ITime(seq(as.ITime("0:00"), as.ITime("23:59:59"), as.ITime("0:06")))
# rolling join and aggregate
ts[, CJ(breaks, group, unique = TRUE)
][ts, on = .(group, breaks = time), roll = -Inf, .(x.breaks, group)
][, .N, by = .(upper = x.breaks, group)]
返回
upper group N 1: 00:06:00 B 2 2: 00:06:00 A 2 3: 00:12:00 A 1 4: 00:12:00 B 1 5: 00:18:00 B 1 6: 00:18:00 A 1 7: 00:24:00 A 1 8: 00:24:00 B 1 9: 00:30:00 A 1
如果滚动连接的方向改变了(由roll = +Inf
代替了roll = -Inf
),我们将得到左闭合间隔
ts[, CJ(breaks, group, unique = TRUE)
][ts, on = .(group, breaks = time), roll = +Inf, .(x.breaks, group)
][, .N, by = .(lower = x.breaks, group)]
这将显着改变结果:
lower group N 1: 00:00:00 B 2 2: 00:00:00 A 2 3: 00:06:00 A 1 4: 00:06:00 B 1 5: 00:12:00 B 1 6: 00:18:00 A 2 7: 00:18:00 B 1 8: 00:30:00 A 1
library(data.table)
ts <- fread("
1 0:03 B 1
2 0:05 A 1
3 0:05 A 1
4 0:05 B 1
5 0:10 A 1
6 0:10 B 1
7 0:14 B 1
8 0:18 A 1
9 0:20 A 1
10 0:23 B 1
11 0:30 A 1"
, header = FALSE
, col.names = c("rn", "time", "group", "value"))