如果數據不很好5分鐘掛鐘邊界上開始(如圖所示在示例數據– 11:13),請注意cut()
將基於它找到的第一個時間戳創建斷點。這可能不是我們通常想要的。事實上,你的樣本輸出表明這不是你想要的。
這裏是cut()
做:
df <- read.table(header=TRUE, sep=",", stringsAsFactors=FALSE, text="
DeviceTime,Concentration
6/20/2013 11:13,1
6/20/2013 11:14,1
6/20/2013 11:15,2
6/20/2013 11:16,2
6/20/2013 11:17,2
6/20/2013 11:18,2
6/20/2013 11:19,2
6/20/2013 11:20,3
6/20/2013 11:21,3
6/20/2013 11:22,3
6/20/2013 11:23,3
6/20/2013 11:24,3
6/20/2013 11:25,4")
df$DeviceTime <- as.POSIXct(df$DeviceTime, format="%m/%d/%Y %H:%M")
cut(df$DeviceTime, breaks="5 min")
[1] 2013-06-20 11:13:00 2013-06-20 11:13:00 2013-06-20 11:13:00
[4] 2013-06-20 11:13:00 2013-06-20 11:13:00 2013-06-20 11:18:00
[7] 2013-06-20 11:18:00 2013-06-20 11:18:00 2013-06-20 11:18:00
[10] 2013-06-20 11:18:00 2013-06-20 11:23:00 2013-06-20 11:23:00
[13] 2013-06-20 11:23:00
means <- aggregate(df["Concentration"],
list(fiveMin=cut(df$DeviceTime, "5 mins")),
mean)
means
fiveMin Concentration
1 2013-06-20 11:13:00 1.600000
2 2013-06-20 11:18:00 2.600000
3 2013-06-20 11:23:00 3.333333
注意的means
(在十一點13分零零秒進入)第一行是第5行的df
,其具有11:13倍的平均到11:17 - 也就是直到下一個11:18的切割/折斷點之前。
你會得到與dplyr(即@ lukeA的答案)相同的結果,如果你使用cut()
:
df %>%
group_by(DeviceTime = cut(DeviceTime, breaks="5 min")) %>%
summarize(Concentration = mean(Concentration))
Source: local data frame [3 x 2]
DeviceTime Concentration
1 2013-06-20 11:13:00 1.600000
2 2013-06-20 11:18:00 2.600000
3 2013-06-20 11:23:00 3.333333
的XTS包似乎通過掛鐘時間打破:
require(xts)
df.xts <- xts(df$Concentration, df$DeviceTime)
means.xts <- period.apply(df.xts, endpoints(df.xts, "mins", k=5), mean)
means.xts
[,1]
2013-06-20 11:14:00 1
2013-06-20 11:19:00 2
2013-06-20 11:24:00 3
2013-06-20 11:25:00 4
時間值始終是最後一次在5分鐘窗口中找到的條目。你可以用align.time()
圓的時間索引列了下一個5分鐘的邊界,如果你想報告期結束的時間:
means.rounded <- align.time(means.xts, 5*60)
means.rounded
[,1]
2013-06-20 11:15:00 1
2013-06-20 11:20:00 2
2013-06-20 11:25:00 3
2013-06-20 11:30:00 4
您也可以四捨五入,如果您要報案時期的開始時間。但是,你需要先定義你自己的功能(這是我在Cross Validated找到):
align.time.down = function(x,n) {
index(x) = index(x) - n
align.time(x,n)
}
means.rounded.down <- align.time.down(means.xts, 5*60)
means.rounded.down
[,1]
2013-06-20 11:10:00 1
2013-06-20 11:15:00 2
2013-06-20 11:20:00 3
2013-06-20 11:25:00 4
另一種解決方案,即不使用XTS包,而是floor()
,如下:
df$DeviceTimeFloor <- as.POSIXct(floor(as.numeric(df$DeviceTime)/(5 * 60)) * (5 * 60), origin='1970-01-01')
meansFloor <- aggregate(Concentration ~ DeviceTimeFloor, df, mean)
meansFloor
DeviceTimeFloor Concentration
1 2013-06-20 11:10:00 1
2 2013-06-20 11:15:00 2
3 2013-06-20 11:20:00 3
4 2013-06-20 11:25:00 4
我寧願報告5分鐘間隔的開始時間– floor()
對此很有幫助。因爲如果我要按小時報告彙總數據,我希望2013-06-20 11:00:00的時間戳包含時間段11:00:00 - 11:59:59而非10:00:00的數據 - 10:59:59。
如果您希望報告間隔的結束時間,可以使用ceiling()
而不是floor()
。但請注意,時間戳11:01 - 11:05將由ceiling()
轉換爲(並因此分組)到11:05。相反,floor()
將11:00 - 11:04轉換爲11:00。
所以他們每個人都有一組不同的觀察值。 xts包將對與floor()
相同的一組觀測進行分組,但它會報告上一次觀測的最後一個時間戳。
'cut'可以將日期/時間對象的中斷設置爲比如說「5分鐘」... – A5C1D2H2I1M1N2O1R2T1
[How to round a time?]的可能重複(http://stackoverflow.com/questions/ 17108515/how-to-round-a-time) –
[每小時步驟值的15分鐘步驟的聚合值]的可能重複(http://stackoverflow.com/questions/17389533/aggregate-values-of-15-分鐘步驟到小時值的步驟) – agstudy