我有一些代码,其中包括for循环和嵌套的if语句。问题是运行时间太长,我想使其更快。
我在名为f2_cebu_davao的数据帧中具有同类群组的数据。此数据框中还有一列称为person_id。同类群组分为3类:“基线”,“其他效果”,“广告系列”。
我想遍历f2_cebu_davao数据框中的每个person_id,并查看其所在的同类群组。如果它在同类群组“基线”或“其他效果”中,那么我将检查before_baseline_othereffects表以查看如果可以在该表中找到该ID。如果可以,我在f2_cebu_davao表中创建一个新列,该值将为“ returning”。否则为“新”。
如果同类群组名称是“ campaign”,我将检查before_campaign表并执行与上述相同的过程。
我的数据很大(我的所有对象都很大),所以这要花很长时间才能运行(已经运行了30多分钟,但还没有完成!)。
我该如何加快速度(可能是通过使用向量化,或者只是稍微修改一下代码)?
我尝试过遍历,但是时间太长了。
before_baseline_othereffects <- subset(loans_final_full, submitted_at_date < '2018-05-21')
before_campaign <- subset(loans_final_full, submitted_at_date < '2019-01-21')
for(i in 1:nrow(f2_cebu_davao)){
if(as.vector(f2_cebu_davao[, 'cohort'][i]) == 'Baseline') {
if(as.vector(f2_cebu_davao[,'person_id'][i]) %in% as.vector(unique(before_baseline_othereffects$person_id)) == TRUE) {
f2_cebu_davao$new_or_returning[i] <- 'Returning'
} else {
f2_cebu_davao$new_or_returning[i] <- 'New'
}
} else if (as.vector(f2_cebu_davao[, 'cohort'][i]) == 'Other Effects'){
if(as.vector(f2_cebu_davao[,'person_id'][i]) %in% as.vector(unique(before_baseline_othereffects$person_id)) == TRUE) {
f2_cebu_davao$new_or_returning[i] <- 'Returning'
} else {
f2_cebu_davao$new_or_returning[i] <- 'New'
}
} else {
if(as.vector(f2_cebu_davao[,'person_id'][i]) %in% as.vector(unique(before_campaign$person_id)) == TRUE) {
f2_cebu_davao$new_or_returning[i] <- 'Returning'
} else {
f2_cebu_davao$new_or_returning[i] <- 'New'
}
}
}
答案 0 :(得分:0)
如果您可以提供一些示例数据和所需的输出,很高兴进行更新和测试。我希望像这样的东西应该可以工作。
我在这里伪造了一些数据:
f2_cebu_davao <- data.frame(stringsAsFactors = F,
cohort = rep(c("Baseline", "Other Effects", "Something else",
"Another Something"), by = 3),
person_id = 1:12
)
before_baseline_othereffects <- c(1:4)
before_campaign <- c(5:8)
在这里,我使用dplyr的case_when
来应用它,拼写出四种情况。这段代码将被矢量化,我希望它将比当前的循环代码快得多。
before_baseline_othereffects
中。这将在第1行和第2行中创建“返回”。before_campaign
中,标记为Returning,如第7和8行所示。library(dplyr)
output <- f2_cebu_davao %>%
mutate(new_or_returning = case_when(
cohort %in% c("Baseline", "Other Effects") &
person_id %in% before_baseline_othereffects ~ "Returning",
cohort %in% c("Baseline", "Other Effects") ~ "New",
person_id %in% before_campaign ~ "Returning",
TRUE ~ "New"
))
以下是输出:
> output
cohort person_id new_or_returning
1 Baseline 1 Returning
2 Other Effects 2 Returning
3 Something else 3 New
4 Another Something 4 New
5 Baseline 5 New
6 Other Effects 6 New
7 Something else 7 Returning
8 Another Something 8 Returning
9 Baseline 9 New
10 Other Effects 10 New
11 Something else 11 New
12 Another Something 12 New