我有一个带有一些Date列的data.table dt。当我聚合表时,我得到一些条目的NA值。这是预期的。但是,该字段实际上不是NA,即使它表明它是NA。当我比较那些NA日期字段时,我没有得到NA,这是可以预期的。我不明白这是一个奇怪的结果,正在对我的分析造成破坏。
> dt <- data.table(cust = c(1,1,2,2,2,3,3)
, DTE_off = as.Date(c('2018-07-31', '2019-05-06', '2014-06-01', '2015-06-01', '2019-05-06', '2018-06-18', '2019-05-06'), '%Y-%m-%d')
, chp_start = as.Date(c('2001-01-22', '2001-01-22', '2000-01-01', '2000-01-01', '2000-01-01', '2000-01-01', '2000-01-01'), '%Y-%m-%d')
, chp_end = as.Date(c('2019-05-05', '2019-05-05', '2019-05-05', '2019-05-05', '2019-05-05', '2019-05-05', '2019-05-05'), '%Y-%m-%d')
, prod_any = c('Y','Y','Y','Y', 'Y','N','N'))
> dt
cust DTE_off chp_start chp_end prod_any
1: 1 2018-07-31 2001-01-22 2019-05-05 Y
2: 1 2019-05-06 2001-01-22 2019-05-05 Y
3: 2 2014-06-01 2000-01-01 2019-05-05 Y
4: 2 2015-06-01 2000-01-01 2019-05-05 Y
5: 2 2019-05-06 2000-01-01 2019-05-05 Y
6: 3 2018-06-18 2000-01-01 2019-05-05 N
7: 3 2019-05-06 2000-01-01 2019-05-05 N
> dt[, month := format(DTE_off, '%Y-%m')]
> dt
cust DTE_off chp_start chp_end prod_any month
1: 1 2018-07-31 2001-01-22 2019-05-05 Y 2018-07
2: 1 2019-05-06 2001-01-22 2019-05-05 Y 2019-05
3: 2 2014-06-01 2000-01-01 2019-05-05 Y 2014-06
4: 2 2015-06-01 2000-01-01 2019-05-05 Y 2015-06
5: 2 2019-05-06 2000-01-01 2019-05-05 Y 2019-05
6: 3 2018-06-18 2000-01-01 2019-05-05 N 2018-06
7: 3 2019-05-06 2000-01-01 2019-05-05 N 2019-05
> dt_agg <- dt[ ,.(last_dte_off = max(DTE_off), any_start = max(chp_start[which(prod_any == "Y")], na.rm = TRUE), any_end = max(chp_end[which(prod_any == "Y")], na.rm = TRUE)) , by = .(cust, month)]
Warning messages:
1: In max.default(numeric(0), na.rm = TRUE) :
no non-missing arguments to max; returning -Inf
2: In max.default(numeric(0), na.rm = TRUE) :
no non-missing arguments to max; returning -Inf
3: In max.default(numeric(0), na.rm = TRUE) :
no non-missing arguments to max; returning -Inf
4: In max.default(numeric(0), na.rm = TRUE) :
no non-missing arguments to max; returning -Inf
当我检查dt_agg中的NA时,没有。但是当我查看数据时,有NA。这些NA有效(它们应该在那里!)
> anyNA(dt_agg)
[1] FALSE
> dt_agg
cust month last_dte_off any_start any_end
1: 1 2018-07 2018-07-31 2001-01-22 2019-05-05
2: 1 2019-05 2019-05-06 2001-01-22 2019-05-05
3: 2 2014-06 2014-06-01 2000-01-01 2019-05-05
4: 2 2015-06 2015-06-01 2000-01-01 2019-05-05
5: 2 2019-05 2019-05-06 2000-01-01 2019-05-05
6: 3 2018-06 2018-06-18 <NA> <NA>
7: 3 2019-05 2019-05-06 <NA> <NA>
更糟糕的是,当我尝试比较dt_agg中的汇总日期字段时,具有NA的条目应返回NA,但它们实际上返回一个值。从技术上讲,这意味着它们不是NA。我不确定发生了什么。
> dt_agg[, compare := any_start > any_end]
> dt_agg
cust month last_dte_off any_start any_end compare
1: 1 2018-07 2018-07-31 2001-01-22 2019-05-05 FALSE
2: 1 2019-05 2019-05-06 2001-01-22 2019-05-05 FALSE
3: 2 2014-06 2014-06-01 2000-01-01 2019-05-05 FALSE
4: 2 2015-06 2015-06-01 2000-01-01 2019-05-05 FALSE
5: 2 2019-05 2019-05-06 2000-01-01 2019-05-05 FALSE
6: 3 2018-06 2018-06-18 <NA> <NA> FALSE # what's going on here?!? compare should be NA, not FALSE
7: 3 2019-05 2019-05-06 <NA> <NA> FALSE # what's going on here?! compare should be NA, NOT FALSE
我认为这与Date类的总和有关。但是,仍然看到不是NA的NA值有点荒谬吗?
答案 0 :(得分:1)
警告与数据中的NA
无关,但是特定组的'prod_any'值不为“ Y”,当我们将which
包装在它们上时,它会给出类似于
which(c(1, 3) == 5)
#integer(0)
,其中max
发出警告
max(which(c(1, 3) == 5), na.rm = TRUE)
#[1] -Inf
警告消息:在max(which(c(1,3)== 5),na.rm = TRUE)中:否 max的不可缺少的参数;返回-Inf
为避免警告,我们可以通过使用if / else条件换行来跳过这些组上的max
dt[, .(last_dte_off = max(DTE_off),
any_start = if(!any(prod_any == "Y")) NA_real_ # changed here
else max(chp_start[which(prod_any == "Y")], na.rm = TRUE),
any_end = if(!any(prod_any == "Y")) NA_real_
else max(chp_end[which(prod_any == "Y")], na.rm = TRUE)),
by = .(cust, month)]
# cust month last_dte_off any_start any_end
#1: 1 2018-07 2018-07-31 2001-01-22 2019-05-05
#2: 1 2019-05 2019-05-06 2001-01-22 2019-05-05
#3: 2 2014-06 2014-06-01 2000-01-01 2019-05-05
#4: 2 2015-06 2015-06-01 2000-01-01 2019-05-05
#5: 2 2019-05 2019-05-06 2000-01-01 2019-05-05
#6: 3 2018-06 2018-06-18 <NA> <NA>
#7: 3 2019-05 2019-05-06 <NA> <NA>
这里没有警告