[英]Speed up for loop with if in r
我有一個名為dataSessions的數據框,其中有3列“時間戳記”,“ CookieID”,“名稱”,其中有130萬行。 已根據CookieID和時間戳進行訂購。
我想創建一個稱為“會話”的新列,根據某些條件顯示1或0。
1的標准是:
1) The previous cookie is not the same as the current
2) The time between the same cookieID is over 30 minutes
我試圖做一個代碼,其中for for循環在每一行中運行,並檢查CookieID是否在此之前。 但是此過程需要很長時間。 有更快,更有效的方法嗎?
dataSessions$Test<-lag(dataSessions$CookieID, n = 1)
for (i in 1:length(dataSessions$CookieID)) {
if(dataSessions$CookieID[i] %in% dataSessions$Test[i]) {
dataSessions$New[i] <- 0
} else {
dataSessions$New[i] <- 1
}
}
這是數據的示例,以及我要生成的SESSIONS列:
Timestamp CookieID Name SESSIONS
2015-08-28 15:46:03 223284 A 1
2015-09-19 22:26:50 223223 A 1
2015-09-19 22:27:09 223223 A 0
2015-09-19 22:28:11 223223 A 0
2015-09-20 22:29:14 245458 B 1
2015-09-20 22:30:17 245458 B 0
2015-09-20 23:05:01 245458 B 1
2015-09-20 23:06:15 245458 B 0
如圖所示,當開始新的CookieID或CookieIDs的最后條目超過30分鍾時,會話數僅為1。
使用data.table
可能有一種更快的方法,但是與此同時:
dd <- read.csv(header=TRUE,
stringsAsFactors=FALSE,text="
Timestamp,CookieID,Name,SESSIONS
2015-08-28 15:46:03,223284,A,1
2015-09-19 22:26:50,223223,A,1
2015-09-19 22:27:09,223223,A,0
2015-09-19 22:28:11,223223,A,0
2015-09-20 22:29:14,245458,B,1
2015-09-20 22:30:17,245458,B,0
2015-09-20 23:05:01,245458,B,1
2015-09-2023:06:15,245458,B,0")
dd$Timestamp <- as.POSIXct(dd$Timestamp)
查找時間差異(以秒為單位,轉換為半小時)-將第一次觀察到“上一個”之間的時間設置為無限:
dt <- c(Inf,diff(dd$Timestamp)/(60*30))
查找Cookie差異:
dcookie <- c(NA,diff(dd$CookieID))
檢查任何一種情況:
dd$SESSIONS <- as.numeric(dcookie!=0 | dt >1)
這里的邏輯是我們正在尋找以下情況
dcookie!=0
:以前的和當前的(數字)cookie值之差不為零(即cookie已更改) dt>1
:上一個時間戳與當前時間戳之差> 1個半小時 在我們可以進行高效循環的環境中(幾乎是R以外的任何語言,例如Python或通過Rcpp
使用C ++代碼),我們希望首先檢查cookie的相等性(快於減法),然后如果 cookie相等,則進行時間差計算-會節省一些時間。
data.table
的答案的data.table替代方法是:
library(data.table)
setDT(df)[, session := +(Timestamp - shift(Timestamp, 1L, "lag") > 1800 |
CookieID != shift(CookieID, 1L, "lag"))
][1, session:=1]
這給出了:
> df
Timestamp CookieID Name session
1: 2015-08-28 15:46:03 223284 A 1
2: 2015-09-19 22:26:50 223223 A 1
3: 2015-09-19 22:27:09 223223 A 0
4: 2015-09-19 22:28:11 223223 A 0
5: 2015-09-20 22:29:14 245458 B 1
6: 2015-09-20 22:30:17 245458 B 0
7: 2015-09-20 23:05:01 245458 B 1
8: 2015-09-20 23:06:15 245458 B 0
使用的數據:
df <- structure(list(Timestamp = structure(c(1440769563, 1442694410, 1442694429, 1442694491, 1442780954, 1442781017, 1442783101, 1442783175), class = c("POSIXct", "POSIXt"), tzone = ""), CookieID = c(223284L, 223223L, 223223L, 223223L, 245458L, 245458L, 245458L, 245458L), Name = structure(c(1L, 1L, 1L, 1L, 2L, 2L, 2L, 2L), .Label = c("A", "B"), class = "factor")), .Names = ("Timestamp", "CookieID", "Name"), row.names = c(NA, -8L), class = "data.frame")
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.