是否可以矢量化/加速使用先前迭代值的FOR循环的执行?
在下面的繁殖示例中:
- 当前产量根据当前库存计算
- 当前生产更新NEXT库存
- 下一次迭代使用更新后的库存来确定当前产量等
所以我需要在每次迭代时计算库存,以便计算生产设置点。。。有可能避免(慢速(循环吗?
目前50k线路的实施时间约为45秒。
# Dummy functions for the examples. Real code is more complicated
function1 <- function(energy, stock, critical) {
if (stock < critical) {
return (energy)
} else {
return(0)
}
}
function2 <- function(power) {
return(round(power/100))
}
# Dummy data
d <- data.frame( "energy"= c(660, 660, 660, 660),
"stock" = c(20, 0, 0, 0),
"delivery" = c(0, 0, 2, 0),
"critical" = c(50, 50 ,50, 50),
"power" = c(0, 0, 0, 0),
"production" = c(0, 0, 0, 0) )
for (i in 1:length(d$energy)) {
# Computing power, based on CUURENT stock
d$power[i] <- function1(d$energy[i], d$stock[i], d$critical[i])
# Computing production
d$production[i] <- function2(d$power[i])
# Updating NEXT stock with current production / delivery
if (i < length(d$energy)) {
d$stock[i+1] <- d$stock[i] + d$production[i] - d$delivery[i]
}
}
View(d)
在基础中,您可以将Reduce
与accumulate = TRUE
一起使用,如:
fun <- function(x,y) {
ttStock <- x[[2]] + x[[6]] - x[[3]]
ttPower <- function1(y[[1]], ttStock, y[[4]])
ttProduction <- function2(ttPower)
c(y[[1]], ttStock, y[[3]], y[[4]], ttPower, ttProduction)
}
d$power[1] <- function1(d$energy[1], d$stock[1], d$critical[1])
d$production[1] <- function2(d$power[1])
do.call(rbind, Reduce(fun, as.data.frame(t(d[-1,])), d[1,], accumulate = TRUE))
# energy stock delivery critical power production
#1 660 20 0 50 660 7
#2 660 27 0 50 660 7
#3 660 34 0 50 660 7
#4 660 39 2 50 660 7
为了更容易,我在d
的第一行中填写了power
和production
。
如果您使用名称而不是列号:
fun <- function(x,y) {
names(x) <- colnames(d)
ttStock <- x[["stock"]] + x[["production"]] - x[["delivery"]]
ttPower <- function1(y[[1]], ttStock, y[[4]])
ttProduction <- function2(ttPower)
c(y[[1]], ttStock, y[[3]], y[[4]], ttPower, ttProduction)
}
一种可能性是使用dplyr
包,它是tidyverse
的一部分。
library(dplyr)
d %>%
mutate(power = function1(energy, stock, critical),
production = function2(power),
stock_new = cumsum(stock + lag(production - delivery, 1, default = 0)))
energy stock delivery critical power production stock_new
1 660 20 0 10 500 5 20
2 660 0 0 10 500 5 25
3 660 0 2 10 500 5 30
4 660 0 0 10 500 5 33
如果函数CCD_ 8和CCD_。如果没有,则必须在mutate
中使用purrr::map
。
如何在函数调用之间保存状态。
my_env <- new.env(parent = emptyenv())
my_env$stock <- d$stock[0]
f <- function(item){
power <- function1()
production <- function1()/100
stock <- my_env$stock
....
rest of the businesss logic
...
}
apply(d, 2, f)