Does anybody know if it is possible to insert a "is proportional to" symbol in an expression string in R?
Use something like this:
expression(x %~~% y)
expression(x %prop% y)
An example
# Approximately equal
x <- 1:10
y <- x + rnorm(10,0,.01)
plot(x, y, main = expression(y %~~% x))
# Proportional to...
x <- 1:10
y <- 3*x
plot(x, y, main = expression(y %prop% x))
Take a look at ?plotmath for documentation and more examples.
Related
I am doing some tasks for my degree and stuck upon a problem of imaging a multivariable function. Following:
fb<-function(x) {5*x[1]^2+2*x[1]*x[2]+4*x[2]^2+4*x[1]-2*x[2]-2}
> x<--50:50
> y<--50:50
> z<-outer(x,y,fb)
Error in FUN(X, Y, ...) : unused argument (Y)
More than that, I need to find an optimum with maximum on point, but it gives out next when I try without vectors:
optim(c(0,0), fb, control=list(fnscale=-5))
Error in fn(par, ...) : argument "y" is missing, with no default
Please advice.
It looks as though you have a function of two variables, x[1] and x[2], that you are passing into your function as a single vector, x. This will cause problems with vectorization of the output. A better way to write it would be
fb <- function(x, y) {
5 * x^2 + 2*x * y + 4 * y^2 + 4 * x - 2 * y - 2
}
This allows you to visualize the function as a surface, for example using persp:
x <- -50:50
y <- -50:50
z <- outer(x, y, fb)
persp(x, y, z)
To get this working with optim, create a wrapper function that puts x and y into a single vector so that it is functionally equivalent to your original function:
result <- optim(c(0, 0), function(x) fb(x[1], x[2]))$par
result
#> [1] -0.4736532 0.3684892
To show this is the correct result, we will plot the optimum point on a 2D representation of the surface.
library(ggplot2)
ggplot(cbind(expand.grid(x = x, y = y), z = c(z)), aes(x, y, fill = z)) +
geom_raster() +
scale_fill_viridis_c() +
geom_point(x = result[1], y = result[2], color = "white")
Created on 2022-06-15 by the reprex package (v2.0.1)
If you want to use outer, you should try it with Vectorize
x <- -50:50
y <- -50:50
z <- outer(x, y, Vectorize(function(a, b) fb(c(a, b))))
and for optiom
> optim(c(0, 0), fb, lower = c(-50, -50), upper = c(50, 50), method = "L-BFGS-B")
$par
[1] -0.4736842 0.3684211
$value
[1] -3.315789
$counts
function gradient
7 7
$convergence
[1] 0
$message
[1] "CONVERGENCE: REL_REDUCTION_OF_F <= FACTR*EPSMCH"
I am trying to solve an optimization problem using two equations. But the derivative of the first equation will be used in the second equation. As you can see below, I need something between c and d. c set the first derivative equal to zero and bring y to the right-hand side, and the y is used in the second equation.
x <- Sym("x")
y <- Sym("y")
a <- function(x, y) (60-x-y)*y
b <- Deriv(a, "y")
c <- Solve(b(x, y)==0, y); c #Need something here to extract just the left-hand side (60 - x)/2; it produces "Yacas vector:[1] y == (60 - x)/2"
y <- function(x) (60 - x)/2
f <- function(x) (60-x-y(x))*x
optimize(f, c(1,100), maximum=TRUE)
I need something that will extract just the right-hand side "(60 - x)/2" and use it as a function.
The question is asking for something that will extract just the right-hand side "(60 - x)/2" and use it as a function .
library(Ryacas)
x <- Sym("x")
y <- Sym("y")
a <- function(x, y) (60-x-y)*y
s <- Solve(deriv(a(x, y), y) == 0, y)
da <- function(x) {}
body(da) <- parse(text = sub("list(y == ", "(", as.character(s), fixed = TRUE))
da
## function (x)
## ((60 - x)/2)
You can do:
x <- Sym("x")
y <- Sym("y")
a <- (60-x-y)*y
b <- deriv(a, y)
c <- Solve(b==0, y)
yacas(paste0("y Where ", c))
# expression((60 - x)/2)
To define the function:
f <- function(x){}
body(f) <- yacas(paste0("y Where ", c))$text
I have a function , foo(x,y), that creates a 3d surface from x,y coordinates. I need to find all values of (x,y) where foo=0. Currently, I am calculating foo at every point on an (x,y) search grid, but this is computationally expensive. Is there a way to give R foo, and have it return all values of (x,y) where foo=0?
With contourLines:
foo <- function(x,y) x^2 + y^2 - 1
x <- y <- seq(-2, 2, len=200)
z <- outer(x, y, foo)
cr <- contourLines(x, y, z, levels=0)
> x <- cr[[1]]$x
> y <- cr[[1]]$y
> foo(x[10], y[10])
[1] -4.438003e-05
I'm trying to write an equation in R (see code below). I was wondering how I can correctly use +- before sqrt() in my code?
x <- seq(0,1,by=0.01)
y <- %+-%sqrt((.5^2)-(x-.5)^2)+.5
Need to plot them separately but the %+-% operator can be used in plotmath expressions. Needs to be flanked by two values, however, hence the need to use the non-printing phantom():
x <- c( seq(0,1,by=0.01) )
y <- c( sqrt((.5^2)-(x-.5)^2)+.5, -sqrt((.5^2)-(x-.5)^2)+.5)
plot( rep(x,times=2), y)
title(main= bquote( phantom(0) %+-% sqrt((.5^2)-(x-.5)^2)+.5))
You may want to have the equation in parametric form, without requiring +- of sqrt.
theta <- seq(0,2*pi,0.01)
x <- 0.5 + 0.5*sin(theta)
y <- 0.5 + 0.5*cos(theta)
plot(x, y)
title(main= substitute(paste('x=(1+sin',theta,')/2, y=(1+cos', theta, ')/2')))
Try this:
draw.circle <- function(stepsize=.01) {
theta <- seq(0,2*pi,by=stepsize)
x <- 0.5 + 0.5*sin(theta)
y <- 0.5 + 0.5*cos(theta)
plot(x, y,type="n",xlim = c(0,1),ylim = c(0,1))
segments(x,y,.5,.5)
}
draw.circle(.01)
draw.circle(.02)
draw.circle(.05)
I would like to plot:
production.ts(31, .002, 10,12,125313.93,211,95,x,"2014-02-01","2014-05-14",z,y) as function of x,y,z
As something like this plot from Mathematica, (if possible in R):
http://i.stack.imgur.com/3PRaf.png
I have a function:
library("lubridate"); library("rgl")
production.ts <- function(a, b, z, c, d, e,
f, g, h, j, r, k) {
elapsed <- (4-z)*10 + (4-c)
un.days <- 100 - elapsed
gone.days <- day(as.Date(h))
rem.days <- day(as.Date(j))
r.days <- as.numeric(as.Date(j) - as.Date(h))
m.r <- f/100*d
inputs <- d * a * (gone.days - 1)/365 + r
prin <- m.r + inputs
costs <- (r.days/365 * r + 1) * prin
added.p <- a/100*d + r
due <- d * 1-un.days
tomr.f <- 1- due + k^2
acct.paid <- (d - due)*tomr.f
net <- added.p + due + acct.paid
pv.net <- net/(1+r*(e-30-day(as.Date(j)))/365)
end <- d - due - acct.paid
more.add.p <- end*a*(rem.days-1)/365
rem <- (f-g)/100 * end
total.fv <- pv.net + rem + more.add.p
out <- costs - total.fv
out
}
x<-seq(-10,10,by=.1)
y<-seq(0,1000,by=.1)
z<-seq(0,90,by=.1)
I have tried:
func.3d<-Vectorize(production.ts(31, .002, 10,12,125313.93,211,95,x,"2014-02-01","2014-05-14",z,y))
c <- func.3d; c <- cut(c,breaks=64); cols <- rainbow(64)[as.numeric(c)]
open3d()
plot3d(x, y, z, col=cols,type="s",size=1)
But this plots lines and the colors don't line up with the values the function should output.
Does anyone know how I could do this? Thanks, I really appreciate your time!
Like this?
x<-seq(-10,10,length=100)
y<-seq(0,1000,length=100)
z<-seq(0,90,length=100)
df <- expand.grid(x=x,y=y,z=z)
f <- function(x,y,z) {production.ts(31, .002, 10,12,125313.93,211,95,x,"2014-02-01","2014-05-14",z,y)}
df$c <- f(df$x,df$y,df$z)
c <- cut(df$c,breaks=64)
cols <- rainbow(64)[as.numeric(c)]
open3d()
plot3d(df$x, df$y, df$z, col=cols,type="p",size=1)
Your code was not plotting lines. When you pass x, y, and z like that to plot3d(...) it cycles through all the elements together, so x[1],y[1],z[1] is a point, x[2],y[2],z[2] is another point, and so on. Since the vectors are different lengths, the shorter ones are recycled to fill out to the length of the longest. The visual effect of this is that the points lie on a line.
You want yo plot every combination of x, y, and z, and give each point a color based on that combination. The code above does that. The plot does not quite look like yours, but I can't tell if that is because of the way you have defined your function.
Also, the way you defined x, y, and z there would be 201 X 10001 X 901 = 1,811,191,101 points, which is too many to handle. The code above plots 1,000,000 points.
Finally, plotting spheres (type="s") is very expensive and unnecessary in this case.