I have a bivariate step function that I want to create a surface of. The function looks essentially as follows:
df<-data.frame(a = rnorm(100, 0, 10), b = rnorm(100, 0, 10))
f<-function(x,y){
mean(df$a * x >= df$b * y)
}
When I use plot3d of the rgl package, I always receive an error message like
Error in dim(zvals) <- dim(xvals) :
dims [product 10201] do not match the length of object [1]
What is the problem here? Is there any alternative how to 3d-plot my function?
The problem is the definition of f. plot3d(f) is going to pass in vectors for x and y, and your function is going to take the mean of everything and return a single value.
The simplest way to fix this is to call the Vectorize function, which wraps f in loops to compute it separately for each x, y pair. For example, with your definition of f as in the question,
plot3d(Vectorize(f), xlim = c(-2,2), ylim = c(-2, 2))
produces this plot:
Related
Let's say I have a series of points between which I want to plot straight lines:
x <- c(0, 2, 4, 7, 12)
y <- c(0, 0, 4, 5, 0)
plot(x, y, type = 'l')
How would I go about turning this plotted line into a simple model object? For instance, something with which I would be able to use the stats::predict() function to do something like this:
model.object <- ???
predict(model.object, data.frame(x = 3))
Output:
2
Or, at the very least, is there some way R can identify the slopes and intercepts of each of these lines between the points so I could manually create a piecewise function using if-statements?
While it's a bit different than predict, you can use approxfun to do interpolation between points
f <- approxfun(x, y)
f(3)
# [1] 2
Note that it just takes a vector of x values rather than a data.frame to make predictions.
I am trying to create a piecewise function using R. I am having trouble with my plot function
a <- function(x){
ifelse(( x <-1),0,ifelse((-1<x & x<2),(x^3+1)/9ifelse((x>2),1,NA)))
}
plot(a,xlim=c(-5,5), ylim = c(-4, 7), col = "red")
I am not sure if I never created my function properly or if there is something wrong with the way that I have plotted it. The piecewise function is a little confusing because it's a straight line of 1 and 0 at its intervals and from -1 to 2 it's a weird function.
There are two typos in your function; one is tricky.
(1) missing a comma before the third ifelse (this is probably a cut-and-paste error); (2) in x<(-1), you need parentheses (or at least a space) so R doesn't think you're assigning the value 1 to x (i.e. x <- 1).
a <- function(x) {
ifelse(( x <(-1)),0,ifelse((-1<x & x<2),(x^3+1)/9,
ifelse((x>2),1,NA)))
}
plot(a,xlim=c(-5,5), ylim = c(-4, 7), col = "red")
I'm solving for the roots of an objective function using the rootSolve package. Here is the code, which give me a plot displaying the roots and prints the solutions:
library(rootSolve)
P_func <- function (x) (0.11)*(-10^6/(10^4-(x/0.03))+20)*(10^4-(x/0.03)^2/(10^6))
curve(P_func(x), 0, 8000)
abline(h = 0, lty = 3)
All <- uniroot.all(P_func, c(0,8000))
points(All, y = rep(0,length(All)), pch = 16, cex = 2)
All
I want to take the roots and plug them into another function:
W_func <- function (x) (10^4-x/0.03)
Where the value of x is defined by each of the solutions I found for P_func. Is there a simple way to do this?
Yes there is indeed a simple way.
All is a vector and your W_func accepts a vector as argument. So just use W_func(All).
I am needing to produce normally distributed density plots with different total areas (summing to 1). Using the following function, I can specify the lambda - which gives the relative area:
sdnorm <- function(x, mean=0, sd=1, lambda=1){lambda*dnorm(x, mean=mean, sd=sd)}
I then want to plot up the function using different parameters. Using ggplot2, this code works:
require(ggplot2)
qplot(x, geom="blank") + stat_function(fun=sdnorm,args=list(mean=8,sd=2,lambda=0.7)) +
stat_function(fun=sdnorm,args=list(mean=18,sd=4,lambda=0.30))
but I really want to do this in base R graphics, for which I think I need to use the "curve" function. However, I am struggling to get this to work.
If you take a look at the help file for ? curve, you'll see that the first argument can be a number of different things:
The name of a function, or a call or an expression written as a function of x which will evaluate to an object of the same length as x.
This means you can specify the first argument as either a function name or an expression, so you could just do:
curve(sdnorm)
to get a plot of the function with its default arguments. Otherwise, to recreate your ggplot2 representation you would want to do:
curve(sdnorm(x, mean=8,sd=2,lambda=0.7), from = 0, to = 30)
curve(sdnorm(x, mean=18,sd=4,lambda=0.30), add = TRUE)
The result:
You can do the following in base R
x <- seq(0, 50, 1)
plot(x, sdnorm(x, mean = 8, sd = 2, lambda = 0.7), type = 'l', ylab = 'y')
lines(x, sdnorm(x, mean = 18, sd = 4, lambda = 0.30))
EDIT I added ylab = 'y' and updated the picture to have the y-axis re-labeled.
This should get you started.
I want to plot a [power function][1] in R, namely 1-\phi(4.65-z/2). This can be written as \int_{-\infty}^{4.65-z/2}\frac{1}{2\pi} \exp(-\frac{x^2}{2}}) in latex.
Can someone explain how to plot this? Is there a specific command for the phi function?
This function, \Phi, is a cumulative distribution function of a standard normal random variable, and yes, there is a function for that in R: dnorm. Hence,
z <- seq(-2, 20, length = 1000)
plot(z, 1 - dnorm(4.65 - z / 2), type = 'l')
# or also just curve(1 - dnorm(4.65 - x / 2), -2, 20)