So, I am able to use the plot() function in R to graph different functions. However, I am finding that the graphs in R do not typically show the entire curve of the function. Let me use an example:
fun <- function(x){
x^3 + 2*x^2 + 3*x + 4
}
plot(fun)
However, when I plot the same function using the Desmos Graphing Calculator it shows all four quadrants of the Cartesian graph whereas R is only showing one:
My question: How can I modify RPlot to show all four quadrants as opposed to just one as in the above case?
I think you can do this just by extending the default range (which is [0,1]):
plot(fun,from=-5,to=5,ylim=c(-8,8),col="red")
grid()
abline(v=0,h=0,lty=2)
I've added a few frills to make it look a little more like the desired plot. Adding a point on the y axis is easy; adding the x-intercept is not quite so easy.
points(0,fun(0),pch=16)
points(Re(polyroot(c(4,3,2,1))[2]),0,pch=16)
Related
Plotting several series in a same plot display is possible and also several subplots in a display. But I want several plots which can be completely different things (not necessarily a series or graph of a map) to be displayed exactly in one frame. How can I do that? In Maple you assign names for each plot like
P1:=...:, P2:= ...: and then using plots:-display(P1,P2,...); and it works. But I want to do this in Julia. Let's say I have the following plots as an example;
using Plots
pyplot()
x=[1,2,2,1,1]
y=[1,1,2,2,1]
plot(x,y)
p1=plot(x,y,fill=(0, :orange))
x2=[2,3,3,2,2]
y2=[2,2,3,3,2]
p2=plot(x2,y2,fill=(0, :yellow))
Now how to have both P1 and P2 in one plot? I don't one a shortcut or trick to write the output of this specific example with one plot line, note that my question is general, for example p2 can be a curve or something else, or I may have a forflow which generates a plot in each step and then I want to put all those shapes in one plot display at the end of the for loop.
Code for a simple example of trying to use plot!() for adding to a plot with arbitrary order.
using Plots
pyplot()
x=[1,2,2,1,1]
y=[1,1,2,2,1]
p1=plot(x,y,fill=(0, :orange))
x2=[2,3,3,2,2]
y2=[2,2,3,3,2]
p2=plot!(x2,y2,fill=(0, :orange))
p3=plot(x,y)
display(p2)
p5=plot!([1,2,2,1,1],[2,2,3,3,2],fill=(0, :green))
By running the above code I see the following plots respectively.
But what I expected to see is a plot with the green rectangle added inside the plot with the two orange rectangles.
The way to plot several series within the same set of axes is with the plot! function. Note the exclamation mark! It's part of the function name. While plot creates a new plot each time it is invoked, plot! will add the series to the current plot. Example:
plot(x, y)
plot!(x, z)
And if you are creating several plots at once, you can name them and refer to them in plot!:
p1 = plot(x, y)
plot!(p1, x, z)
Well, if you do that, what you will have is subplots, technically. That's what it means.
The syntax is
plot(p1, p2)
Sorry, I don't know how to plot a whole plot (conversely to a series) over an other plot.. For what it concerns the order of the plots, you can create as many plots as you want without display them and then display them wherever you want, e.g.:
using Plots
pyplot()
# Here we create independent plots, without displaying them:
x=[1,2,2,1,1]
y=[1,1,2,2,1]
p1=plot(x,y,fill=(0, :orange));
x2=[2,3,3,2,2]
y2=[2,2,3,3,2]
p2=plot(x2,y2,fill=(0, :orange));
p3=plot(x,y);
p5=plot([1,2,2,1,1],[2,2,3,3,2],fill=(0, :green));
# Here we display the plots (in the order we want):
println("P2:")
display(p2)
println("P3:")
display(p3)
println("P5:")
display(p5)
println("P1:")
display(p1)
when using the "curve" function in R, how do you suppress/stop the plot from showing up? For example, this code always plots the curve
my_curve = curve(x)
Is there a parameter to do this or should I being using a different function? I just want the x y points as a dataframe from the curve.
curve() is from the graphics library and is unhandy for generating lists.
Just try using:
x = seq(from, to, length.out = n)
y = function(x)
If you stick to the curve function, the closest to a solution I know is adding dev.off() after the curve() statement!
Here's a way to take advantage of the part of curve that you want without generating a plot.
I made a copy of the curve function (just type curve in the console); called it by a new name (curve2); and commented out the four lines at the end starting with if (isTRUE(add)). When it's called and assigned, I had a list with two vectors—x and y. No plot.
This is the first time I have a R question that I couldn't find on Stack Overflow already - forgive me if the reason why I didn't find anything is a specific term for the type of thing I'm looking for that I'm not aware of (is there?).
I'd like to display data as a cumulative frequency. Since my focus is more on the edges of the Distribution, it is helpful to scale the y-axis to a normal distribution. The result should look something like this:
I've read about quantile-quantile plots, but honestly I can't figure out how to apply them if I want to preserve the X-axis.
I tried both base graphics and ggplot2, but can't figure it out. My current solution is therefore, for example
plot(ecdf(trees$Volume))
or
ggplot(data=trees, aes(Volume)) + stat_ecdf()
I think you are looking for the scales package and the probability_trans() function:
Without transforming the y scales:
require(ggplot2)
ggplot(data = trees,
aes(Volume)) +
stat_ecdf()
With transformation of y axis:
ggplot(data = trees,
aes(Volume)) +
stat_ecdf() +
scale_y_continuous(trans = scales::probability_trans("norm"))
You can read more about these in the documents with ?probability_trans.
The probability_trans() function takes standard R probability names to scale your axis with.
You can also create a new transformation with trans_new() if you need something completely custom.
The qpplot.das function from the StatDA package by Peter Filzmoser might be a "base R" way for you.
library(StatDA)
qpplot.das(trees$Volume, qdist = qnorm, xlab = "Volume", line = FALSE)
output
The StatDA package was used for all calculations and graphics for the book Statistical Data Analysis Explained by Reimann, Filzmoser, Garret and Dutter. All R scripts are online, also examples for the QP plots.
For educational purpose I'm trying to plot a singel horizontal "numberline" with some datapoints with labels in R. I came this far;
library(plotrix)
source("spread.labels.R")
plot(0:100,axes=FALSE,type="n",xlab="",ylab="")
axis(1,pos=0)
spread.labels(c(5,5,50,60,70,90),rep(0,6),ony=FALSE,
labels=c("5","5","50","60","70","90"),
offsets=rep(20,6))
This gave me a numberline with smaller lines pointing up to (and a little bit "in") the labels from where the datapoints should lie on the numberline - but without the points itself. Can anyone give me additional or alternative R-codes for solving thess problems:
- datapoints itself still missing are not plotted,
- and labels maybe not evenly divided over the whole numberline,
- and lines come into the labels and not merely point to the labels
Thank a lot,
Benjamin Telkamp
I usually like to create plots using primitive base R graphics functions, such as points(), segments(), lines(), abline(), rect(), polygon(), text(), and mtext(). You can easily create curves (e.g. for circles) and more complex shapes using segments() and lines() across granular coordinate vectors that you define yourself. For example, see Plot angle between vectors. This provides much more control over the plot elements you create, however, it often takes more work and careful coding than more "pre-packaged" solutions, so it's a tradeoff.
For your case, it sounds to me like you're happy with what spread.labels() is trying to do, you just want the following changes:
add point symbols at the labelled points.
prevent overlap between labels and lines.
Here's how this can be done:
## define plot data
xlim <- c(0,100);
ylim <- c(0,100);
px <- c(5,5,50,60,70,90);
py <- c(0,0,0,0,0,0);
lx.buf <- 5;
lx <- seq(xlim[1]+lx.buf,xlim[2]-lx.buf,len=length(px));
ly <- 20;
## create basic plot outline
par(xaxs='i',yaxs='i',mar=c(5,1,1,1));
plot(NA,xlim=xlim,ylim=ylim,axes=F,ann=F);
axis(1);
## plot elements
segments(px,py,lx,ly);
points(px,py,pch=16,xpd=NA);
text(lx,ly,px,pos=3);
I'm trying to plot an histogram for one variable with ggplot2. Unfortunately, the default binwidth of ggplot2 leaves something to be desired:
I've tried to play with binwidth, but I am unable to get rid of that ugly "empty" bin:
Amusingly (to me), the default hist() function of R seems to produce a much better "segmentation" of the bins:
Since I'm doing all my other graphs with ggplot2, I'd like to use it for this one as well - for consistency. How can I produce the same bin "segmentation" of the hist() function with ggplot2?
I tried to input hist at the terminal, but I only got
function (x, ...)
UseMethod("hist")
<bytecode: 0x2f44940>
<environment: namespace:graphics>
which bears no information for my problem.
I am producing my histograms in ggplot2 with the following code:
ggplot(mydata, aes(x=myvariable)) + geom_histogram(color="darkgray",fill="white", binwidth=61378) + scale_x_continuous("My variable") + scale_y_continuous("Subjects",breaks=c(0,2.5,5,7.5,10,12.5),limits=c(0,12.5)) + theme(axis.text=element_text(size=14),axis.title=element_text(size=16,face="bold"))
One thing I should add is that looking at the histogram produced byhist(), it would seem that the bins have a width of 50000 (e.g. from 1400000 to 1600000 there are exactly two bins); setting binwidth to 50000 in ggplot2 does not produce the same graph. The graph produced by ggplot2 has the same gap.
Without sample data, it's always difficult to get reproducible results, so i've created a sample dataset
set.seed(16)
mydata <- data.frame(myvariable=rnorm(500, 1500000, 10000))
#base histogram
hist(mydata$myvariable)
As you've learned, hist() is a generic function. If you want to see the different implementations you can type methods(hist). Most of the time you'll be running hist.default. So if be borrow the break finding logic from that funciton, we come up with
brx <- pretty(range(mydata$myvariable),
n = nclass.Sturges(mydata$myvariable),min.n = 1)
which is how hist() by default calculates the breaks. We can then use these breaks with the ggplot command
ggplot(mydata, aes(x=myvariable)) +
geom_histogram(color="darkgray",fill="white", breaks=brx) +
scale_x_continuous("My variable") +
theme(axis.text=element_text(size=14),axis.title=element_text(size=16,face="bold"))
and the plot below shows the two results side-by-side and as you can see they are quite similar.
Also, that empty bim was probably caused by your y-axis limits. If a shape goes outside the limits of the range you specify in scale_y_continuous, it will simply get dropped from the plot. It looks like that bin wanted to be 14 tall, but you clipped y at 12.5.