大家好,我正试图运行一个for循环,该循环基于R中多个数据帧向量的某些条件创建一个新变量(由观察ID分割),并且我遇到了一些麻烦。
Dat_nations <- split(Dat, Dat$newccode)
^这创建了143个数据帧的向量,按国家代码分组。我想应用到每个国家数据框的for循环是:
for (i in 1:(length(df1$timeafter)
-1){
df1$timeafter[i+1] <- (df1$newdate[i+1]-df1$newdate[i])
}
本质上,我创建了一个新变量,用于计算特定国家内的观测值在前一个观测值之后出现的天数(它们按日期排序)。但是我不知道如何迭代地在所有数据帧上运行这个,修改每个数据帧,然后将它们全部组合在一起。
非常感谢!
一般来说,处理帧列表的规范方法是使用lapply
,尽管for
循环当然可以工作;有关"框架列表"的一些讨论,请参阅https://stackoverflow.com/a/24376207/3358227。
注:length(df)
是列数,而不是行数。(此外,如果以编程方式使用,1:length(x)
可能是一个错误:如果出于某种原因,参数x
的长度为0,那么人们会希望/期望这返回长度为0的向量,但它返回1:0
又名c(1, 0)
。为了更安全地遍历列,使用seq_along(x)
;要安全地遍历行,请使用seq_len(nrow(x))
。
我认为你可以做你需要的:
lapply(Dat_nations, function(dat) {
dat$timeafter <- c(NA, diff(dat$newdate))
dat
})
顺便说一下,如果你打算然后将其合并回单个帧(出于任何原因),这可以不使用split
(并且可能更快):
Dat$timeafter <- ave(Dat$newdate, Dat$newccode, FUN = function(z) c(NA, diff(z)))
最后注意:当z
属于Date
或POSIXt
类时,diff(z)
将返回difftime
类的数字。这意味着在控制台上它将显示Time difference of 3 days
,而不是显示3
。虽然它看起来像一个字符串,但它仍然是一个数字…dput(diff(Sys.Date()+c(0,3)))+10
(将差值加10)仍然有效。然而,单位可以改变(特别是如果POSIXt
),这是破坏性的。一种简单的方法是使用像
diff(Sys.Date() + c(0, 3))
# Time difference of 3 days
as.numeric(diff(Sys.Date() + c(0, 3)), units = "days")
# [1] 3
as.numeric(diff(Sys.Date() + c(0, 3)), units = "hours")
# [1] 72