50

为什么迭代 a DateorPOSIXct对象会导致numeric? 例如:

test = as.Date("2009-01-01")
print( class( test ) )
# [1] "Date"
for ( day in test )
{
    print( class( day ) )
}
# [1] "numeric"

同样的事情发生在POSIXct

test = as.POSIXct("2009-01-01")
print( class( test ) )
# [1] "POSIXct" "POSIXt"
for ( day in test )
{
    print( class( day ) )
}
# [1] "numeric"
4

6 回答 6

37

?"for"表示seq(后面的部分in)是“[A]n 表达式评估为向量(包括列表和表达式)或配对列表或'NULL'”。

因此,您的Date向量被强制使用,numeric因为Date对象不是严格的向量:

is.vector(Sys.Date())
# [1] FALSE
is.vector(as.numeric(Sys.Date()))
# [1] TRUE

POSIXct向量也是如此:

is.vector(Sys.time())
# [1] FALSE
is.vector(as.numeric(Sys.time()))
# [1] TRUE
于 2011-06-22T04:15:07.887 回答
24

循环天数(字符串):

     days <- seq(from=as.Date('2011-02-01'), to=as.Date("2011-03-02"),by='days' )
     for ( i in seq_along(days) )
     {
          print(i)
           print(days[i])
      }
于 2012-07-24T01:49:21.157 回答
19

Date使用 for 循环时,您没有选择正确的函数来应用于向量。更好的做法是包装seq_along几乎所有循环的日期或因素。然后你将做两件事:a) 设置它,以便你期望一个从 1 开始的索引,以及 b) 防止出现零长度向量的奇怪事情。我还认为将它与因子一起使用会更好,因为 for 循环将变成字符向量。

参考 Joshua 的回答(这肯定是正确且有帮助的),我认为该is.vector功能有点贴错标签或可能只是被误解了。它可以更准确地称为hasNoAttributesOtherThanName。大多数人认为“矢量”的属性经过测试,并且is.atomic对象将从该测试中返回。DatePOSIXctTRUE

于 2011-08-22T04:11:30.937 回答
8

似乎实现for循环的 C 函数不会复制向量的任何属性。这也包括class属性,它应该i看起来是一个Date对象。

您可以在此处研究函数的源代码do_for(SEXP, SEXP, SEXP, SEXP)(由 R 调用的函数for)。

于 2014-04-24T19:49:57.990 回答
6

这是一个老问题,但我是 R 的新手并且面临同样的问题。由于我的问题将被并行处理,我使用了foreach并看到与正常相比的行为有所不同for

library(foreach)

start_date = as.Date("2013-08-1")
end_date = as.Date("2013-08-13")
days = seq(start_date, end_date, by = "day")

foreach(day = days, .combine='rbind') %dopar% {
  print(class(day))
}

[1] "Date"
[1] "Date"
[1] "Date"
[1] "Date"
...

由于我对 R 的大部分内容没有经验,因此我不知道为什么foreach最终会出现不同的行为,但这符合我的目的,希望对其他人有用。

于 2014-07-31T14:24:06.230 回答
1

对日期对象的任何数值运算通常会返回天数。在此,您要求它为您提供从纪元开始的天数。14245 是 1970-01-01 - 2009-01-01 之间的天数

从?日期:

日期表示为自 1970-01-01 以来的天数,较早的日期为负值。它们始终按照当前公历的规则打印,即使该日历很久以前没有使用(它于 1752 年在英国及其殖民地采用)。

日期应该是一个整数,但这在内部表示中没有强制执行。打印时将忽略小数天数。可以通过均值法或加减法产生小数天数(参见 Ops.Date)。

尝试添加print(day)以了解我的意思。

test = as.Date("2009-01-01")
print( class( test ) )
for ( day in test )
{
  print(day)
  print( class( day ) )
}
于 2011-06-22T04:02:14.477 回答