有人能给我解释一下为什么下面的POSIXct时间元素不匹配吗?

我最终try 将向量time中的日期时间值与向量datetime中的日期时间值进行匹配.我简化了该示例,使所有内容都是相同的日期,只有小时值不同.在本例中,我可以使用match来查找datetime中每个time的索引位置.然而,如果我需要将我的约会时间舍入到time到最接近的小时,这里给出的roundtime突然匹配失败?但是time==roundtime呢?我错过了什么吗?

datetime <- as.POSIXct("2020-01-01 15:00:00",tz="UTC") + (0:10) * 3600
time <- as.POSIXct(c("2020-01-01 15:00:00", "2020-01-01 16:00:00", "2020-01-01 21:00:00"),tz='UTC')
roundtime<-round(time,units="hours")

time %in% datetime # gives TRUES
time %in% roundtime # give FALSES?
time == roundtime # gives TRUES
match(time, datetime) # returns matches
match(time, roundtime) # No matches?
match(roundtime, datetime) # no matches?

推荐答案

这个答案扩展了我对OP最初问题的 comments .

该问题似乎归因于使用round导致的静默类更改:

class(time)
[1] "POSIXct" "POSIXt" 
class(datetime)
[1] "POSIXct" "POSIXt" 

class(roundtime)
[1] "POSIXlt" "POSIXt"

类更改在没有警告或注释的情况下执行,并且被默认的S3 print方法隐藏:

print(datetime[1])
[1] "2020-01-01 15:00:00 UTC"
print(time[1])
[1] "2020-01-01 15:00:00 UTC"
print(roundtime[1])
[1] "2020-01-01 15:00:00 UTC"

然而,当对象为unclass%时,这一点很明显:

print(unclass(datetime[1]))
[1] 1577890800
attr(,"tzone")
[1] "UTC"
print(unclass(time[1]))
[1] 1577890800
attr(,"tzone")
[1] "UTC"
print(unclass(roundtime[1]))
$sec
[1] 0

$min
[1] 0

$hour
[1] 15

$mday
[1] 1

$mon
[1] 0

$year
[1] 120

$wday
[1] 3

$yday
[1] 0

$isdst
[1] 0

attr(,"tzone")
[1] "UTC"

match看起来是失败的(尽管它实际上工作正常),因为正如其在线文档中所清楚的那样,"因子、原始向量和列表被转换为字符向量,内部分类的对象通过mtfrm被转换,然后在匹配之前,x和table被强制为公共类型(在R的排序中,两种类型中的后一种,逻辑和数字;复杂和字符).……在某种程度上,什么与什么匹配是一个定义问题".

这个问题可以通过使用lubridate来避免(而且,作为一个额外的好处,我认为相关的函数名使程序员的意图更加透明):

library(lubridate)
roundtime1 <- floor_date(datetime, "hour")
class(roundtime1)
[1] "POSIXct" "POSIXt" 
match(time, roundtime1)
[1] 1 2 7
match(roundtime1, datetime)
 [1]  1  2  3  4  5  6  7  8  9 10 11 

正如@r2evans所写的,这是一个沉默的、令人讨厌的、令人费解的trap (虽然有文档记录,但很容易修复)可能会导致难以识别和避免的意外行为.

R相关问答推荐

向gggplot 2中的数据和轴标签添加大写和星号

如何修复R码的置换部分?

获取列中值更改的行号

如何调整曲线图中的y轴标签?

在RStudio中堆叠条形图和折线图

根据现有列的名称和字符串的存在进行变异以创建多个新列

解析R函数中的变量时出现的问题

将标识符赋给事件序列,避免错误观察

我如何go 掉盒子图底部的数字?

警告消息";没有非缺失的参数到min;,正在返回数据中的inf";.表分组集

在ggplot2上从多个数据框创建复杂的自定义图形

根据r中另一个文本列中给定的范围对各列求和

Conditional documentr::R中数据帧的summarize()

具有自定义仓位限制和计数的GGPLATE直方图

使用&Fill&Quot;在gglot中创建 colored颜色 渐变

如何创建直方图与对齐的每月箱?

在一个multiplot中以非对称的方式在R中绘制多个图

带查找数据的FCT_REORDER.帧

使用另一列中的增长率外推R(使用dplyr)

根据小时-分钟列创建年-月-日序列