r - 将带有因子的数据表的不规则时间序列转换为R中的规则时间序列
问题描述
我正在尝试将数据表的不规则时间序列转换为规则时间序列。我的数据看起来像这样
library(data.table)
dtRes <- data.table(time = c(0.1, 0.8, 1, 2.3, 2.4, 4.8, 4.9),
abst = c(1, 1, 1, 0, 0, 3, 3),
farbe = as.factor(c("keine", "keine", "keine", "keine", "keine", "rot", "blau")),
gier = c(2.5, 2.5, 2.5, 0, 0, 3, 3),
goff = as.factor(c("haus", "maus", "toll", "maus", NA, "maus", "maus")),
huft = as.factor(c(NA, NA, NA, "wolle", "wolle", "holz", "holz")),
mode = c(4, 4, 4, 2.5, NA, 3, 3))
如何通过大约 1 秒的块大小将观察结果聚合成块?(行数可变 - 如果 1 秒内没有行,则为 0)结果应该是数字列的平均值(省略 NA),如果有超过 1 个唯一行,则结果应该是整个重复行的因子价值。如果这对于因子是不可能的或对您没有意义,也可以只取因子列中特定第二个的第一个值。这样,它将是真正的常规时间序列,没有任何重复的时间。如果间隔没有值(例如第二秒的示例),则结果为 NA。
最后结果可能如下所示(取决于是否重复行):
有重复:
wiDups <- data.table(time = c(1, 1, 2, 3, 4, 5, 5),
abst = c(1, 1, NA, 1, NA, 5, 5),
farbe = as.factor(c("keine", "keine", NA, "keine", NA, "rot", "blau")),
gier = c(2.5, 2.5, NA, 0, NA, 4.5, 4.5),
goff = as.factor(c("haus", "maus", NA, "maus", NA, "maus", "maus")),
huft = as.factor(c(NA, NA, NA, "wolle", NA, "holz", "holz")),
mode = c(5, 5, NA, 2.5, NA, 4, 4))
并且没有重复:
noDups <- data.table(time = c(1, 2, 3, 4, 5),
abst = c(1, NA, 1, NA, 5),
farbe = as.factor(c("keine", NA, "keine", NA, "rot")),
gier = c(2.5, NA, 0, NA, 4.5),
goff = as.factor(c("haus", NA, "maus", NA, "maus")),
huft = as.factor(c(NA, NA, "wolle", NA, "holz")),
mode = c(5, NA, 2.5, NA, 4))
将其转换为时间序列对象会更好吗?
解决方案
该问题是 OP 问题 R 的后续问题,将时间序列中的重复行与 datatable 中的不同列类型结合起来。
OP 已要求通过聚合将不规则时间序列转换为规则时间序列。
这可以通过右连接聚合和填充缺失值来实现。
win <- 1 # step size of time series or length of time window
brk <- dtRes[, .(time = tail(scales::fullseq(range(time), win), -1L))]
dtRes[, lapply(.SD, function(x) if (is.numeric(x)) mean(x, na.rm = TRUE)
else unlist(na.omit(unique(x)))),
by = .(time = ceiling(time / win) * win)][
brk, on = .(time)]
time abst farbe gier goff huft mode 1: 1 1 keine 2.5 haus <NA> 4.0 2: 1 1 keine 2.5 maus <NA> 4.0 3: 1 1 keine 2.5 toll <NA> 4.0 4: 2 NA <NA> NA <NA> <NA> NA 5: 3 0 keine 0.0 maus wolle 2.5 6: 4 NA <NA> NA <NA> <NA> NA 7: 5 3 rot 3.0 maus holz 3.0 8: 5 3 blau 3.0 maus holz 3.0
为了创建常规时间序列,使用fullseq()
fromscales
包是为了方便。显然,OP 更喜欢右闭区间,因此可以跳过第一个值。
警告信息
In
`[.data.table`(dtRes, , lapply(.SD, function(x) if (is.numeric(x)) mean(x,
:
第 1 组 j 的结果的第 5 项长度为零。这将填充 3 个 NA 以匹配此结果中最长的列。后面的组可能有类似的问题,但只报告第一个以保存填充警告缓冲区。
可以愉快地忽略。
发出警告是因为huft
是NA
for time == 1
。调用列na.omit()
的结果向量后为huft
空,但组结果有 3 行。因此,data.table
用 填充结果向量NA
以获得匹配的长度——这是我们所期望的。
该解决方案被参数化以使用不同的块大小win
。例如,对于一个块大小win <- 0.5
,我们得到
time abst farbe gier goff huft mode 1: 0.5 1 keine 2.5 haus <NA> 4.0 2: 1.0 1 keine 2.5 maus <NA> 4.0 3: 1.0 1 keine 2.5 toll <NA> 4.0 4: 1.5 NA <NA> NA <NA> <NA> NA 5: 2.0 NA <NA> NA <NA> <NA> NA 6: 2.5 0 keine 0.0 maus wolle 2.5 7: 3.0 NA <NA> NA <NA> <NA> NA 8: 3.5 NA <NA> NA <NA> <NA> NA 9: 4.0 NA <NA> NA <NA> <NA> NA 10: 4.5 NA <NA> NA <NA> <NA> NA 11: 5.0 3 rot 3.0 maus holz 3.0 12: 5.0 3 blau 3.0 maus holz 3.0
有更多的行要填写。
对于win <- 2
我们得到的块大小
time abst farbe gier goff huft mode 1: 2 1 keine 2.5 haus <NA> 4.0 2: 2 1 keine 2.5 maus <NA> 4.0 3: 2 1 keine 2.5 toll <NA> 4.0 4: 4 0 keine 0.0 maus wolle 2.5 5: 6 3 rot 3.0 maus holz 3.0 6: 6 3 blau 3.0 maus holz 3.0
每个时间间隔具有多行的时间序列不是常规时间序列,恕我直言。稍加修改,我们可以得到
win <- 1
brk <- dtRes[, .(time = scales::fullseq(range(time), win)[-1L])]
dtRes[, lapply(.SD, function(x) if (is.numeric(x)) mean(x, na.rm = TRUE)
else list(na.omit(unique(x)))),
by = .(time = ceiling(time / win) * win)][
brk, on = .(time)]
time abst farbe gier goff huft mode 1: 1 1 keine 2.5 haus,maus,toll 4.0 2: 2 NA NA NA 3: 3 0 keine 0.0 maus wolle 2.5 4: 4 NA NA NA 5: 5 3 rot,blau 3.0 maus holz 3.0
现在,每个时间步长只有一行,因为多个因子值已聚合在一个列表元素中。
推荐阅读
- django-rest-framework - rest_framework 自定义 order_by
- maven - 使用 gradle 构建开源依赖项
- javascript - 如何检查一个类是否具有css属性并根据该类更改其他类的css属性
- r - 沿非方形块对角线的部分行总和
- html - 我可以使用 HTTP 请求登录到此 URL 吗?
- javascript - JQuery Validator 两挖
- angular - mousemove 停止时触发事件
- javascript - 在 Vuejs 中按空格键更新自动建议
- java - 兼容性 JDBC 驱动程序版本和 PostgreSQL 版本
- python - 如何使用 Python 在 Selenium Webdriver 中有效地迭代表号?