2

我想在数据表中总结一组观察结果,并可以在语法上使用一些帮助。

我认为这就像连接一样简单,但我试图确定在特定观察日看到的特定值,即使它在当天跨越多个测量值或传感器。

  • 观察结果按日期汇总
  • 观察日期有不同的测量计数(每个日期的行数)
  • “测量”列表示当天在任何传感器中都观察到了特定值。

我创建了 2 个样本数据集,希望能阐明目标。我还创建了一个 Excel 电子表格的图像,希望显示数据之间的关系。

library(data.table)
raw <- data.table(
  Date = as.Date(c("2013-5-4","2013-5-4","2013-5-4", "2013-5-9","2013-5-9", "2013-5-16","2013-5-16","2013-5-16", "2013-5-30")),
  S1 = c(4, 2, 3, 1, 1, 8, 7, 3, 3),
  S2 = c(2, 5, 2, 4, 4, 9, 1, 6, 4),
  S3 = c(6, 2, 2, 7, 3, 2, 7, 2, 1)
)

summarized <- data.table(
  Date = as.Date(c("2013-5-4", "2013-5-9", "2013-5-16", "2013-5-30")),
  M1 = c(FALSE,TRUE,TRUE,TRUE),
  M2 = c(TRUE,FALSE,TRUE,FALSE),
  M3 = c(TRUE,TRUE,TRUE,TRUE),
  M4 = c(TRUE,FALSE,FALSE,TRUE),
  M5 = c(TRUE,FALSE,FALSE,FALSE),
  M6 = c(TRUE,FALSE,TRUE,FALSE),
  M7 = c(FALSE,TRUE,TRUE,FALSE),
  M8 = c(FALSE,FALSE,TRUE,FALSE),
  M9 = c(FALSE,FALSE,TRUE,FALSE),
  M10 = c(FALSE,FALSE,TRUE,FALSE)
)

显示数据集之间关系的 Excel 图像 Excel

原始是测量输入。多个测量可以发生在同一观察日期(即多行)。

总结是我希望得到的。行被汇总,“m”测量列仅表明在任何 V 列中当天观察到的值(在 M 之后,即 M1、M2 之后)。例如,在 5/16 的第一次和最后一次观察中看到了数字 2,但在 5/16 的 9 个值中的任何一个中都没有看到数字 5。

我想我需要使用连接,但如何计算 M 列让我无法理解。

任何帮助深表感谢。

问题:这种类型的操作在数据科学或数学中有名称吗?

更新:我正在尝试以下

setkey(raw,Date)
s <- data.table( Date=unique(raw$Date)) # get a datatable of the unique dates
setkey(s,Date)
s[raw, M1:=(length(na.omit(match(c(raw$V1,raw$v2,raw$v3),1)))>=1)]

请注意,这些值不是 5-4 的预期值(应该是 FALSE)。我认为这是因为原始行在我的匹配语句中不受限制。

         Date   M1
1: 2013-05-04 TRUE
2: 2013-05-09 TRUE
3: 2013-05-16 TRUE
4: 2013-05-30 TRUE

我的猜测是我需要使用不同的方法来对连接中的原始行进行子集化。

4

2 回答 2

3

这似乎有效:

raw[,lapply(1:10,`%in%`,unique(unlist(.SD))),by=Date]

结果是

         Date    V1    V2   V3    V4    V5    V6    V7    V8    V9   V10
1: 2013-05-04 FALSE  TRUE TRUE  TRUE  TRUE  TRUE FALSE FALSE FALSE FALSE
2: 2013-05-09  TRUE FALSE TRUE  TRUE FALSE FALSE  TRUE FALSE FALSE FALSE
3: 2013-05-16  TRUE  TRUE TRUE FALSE FALSE  TRUE  TRUE  TRUE  TRUE FALSE
4: 2013-05-30  TRUE FALSE TRUE  TRUE FALSE FALSE FALSE FALSE FALSE FALSE

如果您想要使用“M”而不是“V”的列,请使用c(M=1:10).1:10

于 2013-09-18T14:21:50.703 回答
1

这是一个重塑问题。

首先,由于数据来自哪个传感器并不重要,让我们将您的三列聚合为一列。

temp <- raw[,Reduce(union,list(S1,S2,S3)),by=Date]

现在我们要从“长”格式重塑为“宽”格式。

这个答案借来的数据表解决方案:

setkey(temp,Date,V1)
temp[CJ(unique(Date),unique(V1)), list(.N)][,
  setNames(as.list(as.logical(N)), paste0("M",unique(V1))), by = Date]
         # Date    M1    M2   M3    M4    M5    M6    M7    M8    M9
# 1: 2013-05-04 FALSE  TRUE TRUE  TRUE  TRUE  TRUE FALSE FALSE FALSE
# 2: 2013-05-09  TRUE FALSE TRUE  TRUE FALSE FALSE  TRUE FALSE FALSE
# 3: 2013-05-16  TRUE  TRUE TRUE FALSE FALSE  TRUE  TRUE  TRUE  TRUE
# 4: 2013-05-30  TRUE FALSE TRUE  TRUE FALSE FALSE FALSE FALSE FALSE

基地reshape以这种方式工作:

as.data.table(reshape(temp, timevar = "V1", v.names = "V1", idvar = "Date", direction = "wide"))
         # Date V1.4 V1.2 V1.3 V1.5 V1.6 V1.1 V1.7 V1.8 V1.9
# 1: 2013-05-04    4    2    3    5    6   NA   NA   NA   NA
# 2: 2013-05-09    4   NA    3   NA   NA    1    7   NA   NA
# 3: 2013-05-16   NA    2    3   NA    6    1    7    8    9
# 4: 2013-05-30    4   NA    3   NA   NA    1   NA   NA   NA

## to order by column
temp2 <- as.data.table(reshape(temp[order(V1)], timevar = "V1", v.names = "V1", idvar = "Date", direction = "wide"))
         # Date V1.1 V1.2 V1.3 V1.4 V1.5 V1.6 V1.7 V1.8 V1.9
# 1: 2013-05-09    1   NA    3    4   NA   NA    7   NA   NA
# 2: 2013-05-16    1    2    3   NA   NA    6    7    8    9
# 3: 2013-05-30    1   NA    3    4   NA   NA   NA   NA   NA
# 4: 2013-05-04   NA    2    3    4    5    6   NA   NA   NA

##converts to logical true/false
temp2[,lapply(.SD,function(x) {x[is.na(x)] <- 0; as.logical(x)}), by = Date]
       # Date   vv  V1.1  V1.2 V1.3  V1.4  V1.5  V1.6  V1.7  V1.8  V1.9
# 1: 2013-05-09 TRUE  TRUE FALSE TRUE  TRUE FALSE FALSE  TRUE FALSE FALSE
# 2: 2013-05-16 TRUE  TRUE  TRUE TRUE FALSE FALSE  TRUE  TRUE  TRUE  TRUE
# 3: 2013-05-30 TRUE  TRUE FALSE TRUE  TRUE FALSE FALSE FALSE FALSE FALSE
# 4: 2013-05-04 TRUE FALSE  TRUE TRUE  TRUE  TRUE  TRUE FALSE FALSE FALSE

这个包reshape2更直观一点:

require(reshape2)
## dummy variable for TRUE/FALSE
temp[,vv := TRUE]
temp_reshape2 <- as.data.table(dcast(temp, Date ~ V1, value.var = "vv"))
## replace NA with FALSE
temp_reshape2[, lapply(.SD, function(x) {x[is.na(x)] <- FALSE; x}), by = Date]
         # Date     1     2    3     4     5     6     7     8     9
# 1: 2013-05-04 FALSE  TRUE TRUE  TRUE  TRUE  TRUE FALSE FALSE FALSE
# 2: 2013-05-09  TRUE FALSE TRUE  TRUE FALSE FALSE  TRUE FALSE FALSE
# 3: 2013-05-16  TRUE  TRUE TRUE FALSE FALSE  TRUE  TRUE  TRUE  TRUE
# 4: 2013-05-30  TRUE FALSE TRUE  TRUE FALSE FALSE FALSE FALSE FALSE

为了完成,一个蹩脚的解析评估解决方案:

limits <- temp[,c(min(V1),max(V1))]
sapply(temp[,min(V1) : max(V1)], function(x) {
temp[,eval(parse(text=paste0("M",x," := any(abs(V1 - ",x,") < .Machine$double.eps)"))),by = Date]
})
于 2013-09-18T17:21:51.730 回答