Reputation: 640
I need to run a function for a set of inputs. There are 4 inputs (pd, cl, va, co) for 5 different situations (5 rows in the "inputs" dataframe). The function should run for each row, accross 100 values of P. And retain the response that minimizes the difference against a givin parameter (ratio in this case).
Below is a reproducible example.
The problem I have is that it seems to run well only for the first input row. Therefore, it gives me this error: Error in $<-.data.frame`(`*tmp*`, min.diff, value = list(response = 20.091674500638)) : replacement has 1 row, data has 5".
Going around this several hours but was not able to figure out the error.
Any hint?
Thanks a lot in advance
inputs <- data.frame(pd=c(38, 50, 50, 86, 38),
cl=c(15, 40, 30, 81, 15),
va=c(150, 145, 160, 141, 150),
co=c(3.0, 4.5, 4.0, 4.8, 1.5))
P <- c(seq(0,150,length.out=100))
eq1 <- function(a,b,c,x){
(a*exp(-((((exp(b)*x))/1000))+c+b))/1000
}
resp.function <- function(pd, cl, va, co, P){
a <- 10000 + 0.01*pd + (-0.1*cl)
b <- 2
c <- -1
ratio <- co / (va/1000)
min.diff <- as.data.frame(eq1(a,b,c,P)) %>%
rename(response = "eq1(a, b, c, P)") %>%
mutate(diff=abs(response - ratio)) %>%
slice(which.min(diff)) %>%
select(response)
return(min.diff)
}
inputs$min.diff <- resp.function(inputs$pd, inputs$cl, inputs$va, inputs$co, P)
Upvotes: 1
Views: 204
Reputation: 24838
The reason you are getting that error is because your function, as written, only returns 1 value. There are 5 columns of inputs
, so that doesn't work.
A base R approach to this is to use the apply
function.
inputs$min.diff <- apply(inputs,MARGIN=1,function(x){resp.function(x["pd"], x["cl"], x["va"], x["co"], P)})
The second argument of apply
indicates which direction to apply to. 1
indicates row wise, and 2
indicates column wise.
As you may know, your function resp.function
does not actually use the arguments that you pass other than P
. I don't believe there is enough information in your post for me to deduce the appropriate function, but if you clarify your intent, I may be able to help.
Upvotes: 2