non-numeric argument to binary operator in integration in R - r

f1 = function(t){exp(-t^2)}
phi1 = function(theta){
0.5-1/sqrt(pi)*integrate(f1, lower = 0, upper = (10-theta)/(2*sqrt(2)))}
mu1 = (450*barx)/(454)
sigs1 = 36/454
pi_thetapost = function(theta){
(1/sqrt(2*pi*sigs1))*exp(-((theta-mu1)^2)/(2*sigs1))}
E_phipost = integrate(phi1*pi_thetapost, lower = -Inf, upper =Inf)
I was trying to do a integration, and I got the error says:
non-numeric argument to binary operator
I think that * is a binary operator, but I am not sure how to figure this out.
Thanks~

A few problems here. First barx isn't defined. But the main problem is that you can't just multiple functions in R. You can multiple the values returns by function, but not the functions themselves. You need to pass in a proper function to integrate.
But then after that problem, you need to make sure all the functions you pass in to integrate() are vectorized and your phi function is not. you need to be able to pass in a vector and get a vector out. The easiest way to fix this is with Vectorize(). And finally, integrate() returns an object, not just a number. So if you want to return the calculated value, you need to extract it from the object before you can multiply it by another object. Try
f1 <- function(t){
exp(-t^2)
}
phi1 <- function(theta) {
0.5-1/sqrt(pi)*integrate(f1, lower = 0, upper = (10-theta)/(2*sqrt(2)))$value
}
barx <- 2 # or whatever
mu1 <- (450*barx)/(454)
sigs1 <- 36/454
pi_thetapost <- function(theta){
(1/sqrt(2*pi*sigs1))*exp(-((theta-mu1)^2)/(2*sigs1))
}
myfun <- function(x) {
Vectorize(phi1)(x)*pi_thetapost(x)
}
E_phipost <- integrate(myfun, lower = -Inf, upper =Inf)
E_phipost
# 3.690467e-05 with absolute error < 5.6e-05
E_phipost$value
# [1] 3.690467e-05

Related

apply Integrate function to a vector

I'm a newbie to R programming and I have an assignment to submit so my prob is the following:
I wrote the following function :
and I should be using integrate () function to calculate phi(x) for all x
of the vector quantiles and store them in a vector named probs.
I started the following and I got blocked
Rep <- function (x) {
vector <-integrate (phi, lower = Inf , upper = x)$Value }
Not sure if this is the right way to apply the function integrate() to a vector.
Your help is much appreciated
You could do the following:
phi <- function(x)exp(-x^2/2)/sqrt(2 * pi)
quantiles <- seq(from = 0, to = 5.5, by = 0.01)
fun<-Vectorize(function(x)integrate(phi,-Inf, x)[[1]])
fun(quantiles)

Finding optimal parameter for each input combination in the objective function in an optimization

I am calibrating a model and for that I have to estimate a parameter for each input combination I give to the objective function. I have a bit more than 10k input combinations and I want to minimize the parameter for each combination. All other variables in the model are known. I achieved to estimate 1 minimal value for the whole set but that doesn't help me, and when I tried my approach for each combination I get the error: Error in mP[, logik] <- mPv[, logik, drop = FALSE] : NAs are not allowed in subscripted assignments.
My objective function looks like this
x_vol <- vector(mode = "double", length = 10776)
objective_function_vol <- function(x_vol){
S <- calibration_set$index_level
K <- calibration_set$strike
tau <- calibration_set$tau
r <- calibration_set$riskfree_rate
q <- calibration_set$q
model_prices_vol <- vector(mode = "double", length = 10776)
for (i in 1:10776){
model_prices_vol[i] <- hestonCallcf(S = S[i], K = K[i], t = tau[i],
r = r[i], q = 0,
v0 = x_vol[i],
vbar = 0.1064688, rho = -0.9914710,
a = 1.6240300, vvol = 0.98839192)
print(i)
}
diff_sq <- (market_price - model_prices_vol)^2
wdiff <- diff_sq/market_price
error <- sum(wdiff)/10776
return(error)
}
I am using NMOF::DEopt for the optimization. Is it maybe possible to write a second loop which stores the optimal values of x_vol because I think using the subscript i for the known inputted values as well as the unknown is somehow wrong.
The error means that some objective-function calls resulted in NA.
If you only wish to minimize a single parameter (i.e. a scalar), Differential Evolution is probably not the method you want. A grid search along one dimension, possibly with refinements, would likely work better.

Integrate a function and specify other parameters in r

Let's say I want to integrate the function
integrand <- function(x, a) exp(a*x)
where x is my covariate and a is simply a number specified by the user. How do I integrate this in R? I know you can do something like:
integrand <- function(x) {1/((x+1)*sqrt(x))}
integrate(integrand, lower = 0, upper = Inf)
But how can I supply other parameters? I am thinking that I probably need some kind of expression or eval function, but I am not sure how to implement it.
try:
integrand <- function(x, a) exp(a*x)
integrate(integrand, lower = 0, upper = Inf, a=-1)
Have a look at ?integrate and you'll see
integrate(f, lower, upper, ..., subdivisions = 100L,
rel.tol = .Machine$double.eps^0.25, abs.tol = rel.tol,
stop.on.error = TRUE, keep.xy = FALSE, aux = NULL)
Arguments
f an R function taking a numeric first argument and returning a numeric vector of the same length. Returning a non-finite element will generate an error.
lower, upper the limits of integration. Can be infinite.
... additional arguments to be passed to f.
So you can pass as many arguments as integrand needs as fourth argument and they will be passed to the function before integrating it.

Integrate a function in R through time

I would like to integrate the following function with respect to t, for lower bound = 0 and upper bound = t. I can do that with the following code, but my ultimate goal is to have a value of the integral for each t. Even if I make t a sequence instead of a value, or if I try and use sapply, I still cannot get a value for the integral at each step of t.
#initialize constants
kap=-0.1527778
alph0<-6
b<-0
po<-0.01
t<-100
gp_st<-integrate(function(t) (1-alph0/(alph0+b*t)*(1-po^kap))^(1/kap),lower=0,upper=t)$value
#try alternate where t is now a sequence
t<-seq(1:100)
gp_st2<-function(h) sapply(h,gp_st) #still gives length of 1
Thanks!
Try making gp_st a function of your upper bound, like so:
gp_st <- function(h) {
integrate(function(t) (1-alph0/(alph0+b*t)*(1-po^kap))^(1/kap),lower=0,upper=h)$value
}
Then you can use sapply much as you intended:
t<-seq(1:100)
gp_st2 <- sapply(t, gp_st)
and now gp_st2 is a numeric vector of length 100.
The problem is that you are evaluating the integral in gp_st, and you don't want to do that. You want the following:
ff = function(t) {
(1-alph0/(alph0+b*t)*(1-po^kap))^(1/kap)
}
sapply(1:100, function(ul) {
integrate(ff, lower = 0, upper = ul)$value
})
There are naturally more efficient ways to do this.

Compute multiple Integral and plot them (with R)

I'm having trouble to compute and then plot multiple integral. It would be great if you could help me.
So I have this function
> f = function(x, mu = 30, s = 12){dnorm(x, mu, s)}
which i want to integrate multiple time between z(1:100) to +Inf to plot that with x=z and y = auc :
> auc = Integrate(f, z, Inf)
R return :
Warning message:
In if (is.finite(lower)) { :
the condition has length > 1 and only the first element will be used
I have tested to do a loop :
while(z < 100){
z = 1
auc = integrate(f,z,Inf)
z = z+1}
Doesn't work either ... don't know what to do
(I'm new to R , so I'm already sorry if it is really easy .. )
Thanks for your help :) !
There is no need to do the integrating by hand. pnorm gives the integral from negative infinity to the input for the normal density. You can get the upper tail instead by modifying the lower.tail parameter
z <- 1:100
y <- pnorm(z, mean = 30, sd = 12, lower.tail = FALSE)
plot(z, y)
If you're looking to integrate more complex functions then using integrate will be necessary - but if you're just looking to find probabilities for distributions then there will most likely be a function built in that does the integration for you directly.
Your problem is actually somewhat subtle, and in a certain sense gets to the core of how R works, so here is a slightly longer explanation.
R is a "vectorized" language, which means that just about everything works on vectors. If I have 2 vectors A and B, then A+B is the element-by-element sum of A and B. Nearly all R functions work this way also. If X is a vector, then Y <- exp(X) is also a vector, where each element of Y is the exponential of the corresponding element of X.
The function integrate(...) is one of the few functions in R that is not vectorized. So when you write:
f <- function(x, mu = 30, s = 12){dnorm(x, mu, s)}
auc <- integrate(f, z, Inf)
the integrate(...) function does not know what to do with z when it is a vector. So it takes the first element and complains. Hence the warning message.
There is a special function in R, Vectorize(...) that turns scalar functions into vectorized functions. You would use it this way:
f <- function(x, mu = 30, s = 12){dnorm(x, mu, s)}
auc <- Vectorize(function(z) integrate(f,z,Inf)$value)
z <- 1:100
plot(z,auc(z), type="l") # plot lines

Resources