【问题标题】:How to subtract datetimes and store them in a separate column?如何减去日期时间并将它们存储在单独的列中?
【发布时间】:2016-11-20 01:07:05
【问题描述】:

我正在使用 csv 文件,并且我有一个名为“statistics_lastLocatedTime”的列,如图所示 csv file image 我想从第一行中减去第二行“statistics_lastLocatedTime”;从第二行开始的第三行,以此类推直到最后一行,然后将所有这些差异存储在单独的列中,然后将该列与其他相关列合并,如下面的代码所示:

##select related features
data <- read.csv("D:/smart tech/store/2016-10-11.csv")
(columns <- data[with(data, macAddress == "7c:11:be:ce:df:1d" ),
    c(2,10,11,38,39,48,50) ])
write.csv(columns, file = "updated.csv", row.names = FALSE)

## take time difference 
date_data <- read.csv("D:/R/data/updated.csv")
(dates <- date_data[1:40, c(2)])
NROW(dates)
for (i in 1:NROW(dates)) {
  j <- i+1
  r1 <- strptime(paste(dates[i]),"%Y-%m-%d %H:%M:%S")
  r2 <- strptime(paste(dates[j]),"%Y-%m-%d %H:%M:%S")
  diff <- as.numeric(difftime(r1,r2))
  print (diff)
}

## combine time difference with other related columns
combine <- cbind(columns, diff)
combine

现在的问题是我能够获得行的差异,但无法将这些值存储为一列,然后将该列与其他相关列组合。请帮我。提前致谢。

【问题讨论】:

  • 为什么要将date_data 过滤到前 40 行?这将无法 cbind 回columns
  • 实际上 macAddress == "7c:11:be:ce:df:1d" 中的总行数只有 40 行,如果我使用 (dates
  • 您想计算statistics_lastLocatedTime 中的差异,并将该向量存储回数据框中。
  • 不需要 for 循环,diff() 可以对向量进行操作。无需重复将每对日期时间从字符串转换为日期时间,只需使用read.csv() 将它们作为日期时间读取

标签: r csv datetime diff date-arithmetic


【解决方案1】:

这是一个四线:

  1. 根据Specify custom Date format for colClasses argument in read.table/read.csv 定义自定义类“myDate”和自定义日期时间的转换器函数
  2. 将日期时间作为实际日期时间读入;以后无需重复转换。
  3. 只需在日期列上使用矢量化差异运算符(它会看到它们的类型,并自动为 POSIXct 日期分派差异函数)。不需要 for 循环:

.

setClass('myDate') # this is not strictly necessary
setAs('character','myDate', function(from) { 
  as.POSIXct(from, format='%d-%m-%y %H:%S', tz='UTC') # or whatever timezone
})

data <- read.csv("D:/smart tech/store/2016-10-11.csv",
            colClasses=c('character','myDate','myDate','numeric','numeric','integer','factor'))
# ...
data$date_diff <- c(NA, diff(data$statistics_lastLocatedTime))

请注意,diff() 产生的结果长度比我们区分的向量短一。因此,我们必须填充它(例如,使用前导 NA 或任何您想要的)。

【讨论】:

  • 很好的答案!我正在将setAs() 添加到我的图书馆。但是,您可能需要添加 setClass('myDate') 否则会出现错误:no definition for class “myDate”。我怎么会错过diff()?请务必修复 colClasses 中 integer 的结尾引号。
  • @Parfait 不,我们不需要添加setClass('myDate')。没有也能正常工作
  • 原来这是一个警告而不是错误,但仍然按照这个问题的指示进行处理:stackoverflow.com/questions/14146341/…
  • @smci :非常感谢您的帮助。 1)read.csv 中缺少右括号 2)我的输出为 NA,当我删除 as.POSIXct 中的格式时,它工作正常
  • @WaqasBari:谢谢,但我不明白删除格式选项有何改变; format(NA...) 仍然是 NA
【解决方案2】:

考虑使用vapply 直接分配diff 变量。此外,不需要单独的 date_data df,因为所有操作都可以在 columns df 上运行。还要注意时间格式的变化以与数据框中当前的格式保持一致:

columns$diff <- vapply(seq(nrow(columns)), function(i){      
  r1 <- strptime(paste(columns$statistics_lastLocatedTime[i]),"%d-%m-%y %H:%M")
  r2 <- strptime(paste(columns$statistics_lastLocatedTime[i+1]),"%d-%m-%y %H:%M")

  diff <- difftime(r1, r2)      
}, numeric(1))

【讨论】:

    猜你喜欢
    • 2019-05-23
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-06-11
    • 2013-08-10
    相关资源
    最近更新 更多