I am trying to print a "greater or equal to" sign an an R base plot. I have tried both with expression() and bquote() and I simply do not understand what is going wrong.
There is no need for long code, according to plotmath documenmtation this
expression(>=)
should return a vector of type "expression" containing its arguments (unevaluated). Therefore, it should return expression(>=). As is the case for
> expression(phi)
expression(phi)
I keep getting
> expression(>=)
Error: unexpected '>=' in "expression(>="
irrespective of the surrounding code.
You can wrap >= in backquotes, which turns the symbol into a name, but it will be displayed as two symbols, not one. Use expression("" >= "") to get the symbol you probably want. For example,
plot(1, xlab = expression(`>=`), ylab = expression("" >= ""))
Created on 2022-11-25 with reprex v2.0.2
Related
Let's say I have
paste0("Year = ",index,"\nN = ",length((dfGBD %>% filter(year==index))[[vbl]]),
" Bandwidth = ",round(stats::bw.nrd(log((dfGBD %>% filter(year == index))[[vbl]])),2),
"\nSkewness:", round(e1071::skewness(log((dfGBD %>% filter(year==index))[[vbl]])), 2),
" Kurtosis:",round(e1071::kurtosis(log((dfGBD %>% filter(year==index))[[vbl]])),2),
"\nmu[",vbl,"] = ", round(mean((dfGBD %>% filter(year==index))[[vbl]]),2),
" sigma[",vbl,"] = ",round(sd((dfGBD %>% filter(year==index))[[vbl]]),2)
)
inside a sapply through index years. Further, vbl is a string with the name of a variable. The sapply produces a vector of labels for a factor variable.
Applying ggplot I obtain labels similar to the next:
Year = 2000
N = 195 Bandwidth = 0.09
Skewness: 0 Kurtosis: -0.56
mu[Mortality] = 7750.85 sigma[Mortality] = 1803.28
Till here, all ok. I have already written mu[vbl], sigma[vbl] thinking in parsing and subscript notation to get the greek letters with the name of the variable saved in vbl as subscript.
First I tried facet_wrap with option labeller = "label_parsed". I obtained an error which I only solved writting the string between backticks ``, but then \n has no effect. I tried many options using bquote and/or parse and/or expression and/or atop etc. in order to get this multiple lines result with the desired output I described above. But only get or one line or very ugly outputs or, mostly, errors, and I couldn't see yet the greek letters.
So what/how should I do?
PS: as answered in other stackoverflow's, \n does not work in this context, so a list with bquote's for each line is suggested. I tried it, but then I got an error that I think is due to incompatibility of number of elements of all the lists and number of labels of a factor (a label may not be a list?).
Thank you!
This is almost what I want as a plot heading:
plot(1:10)
ylabs<-c("All","Native","Exotic")
i=1
mtext(bquote("("*.(letters[i])*")"~.(ylabs[i])~"("%~~%italic("H'")*")"),side=3)
But I don't want the space after "(" and before the approx. equal sign. Adding the * separator before the symbol gives an error
mtext(bquote("("*.(letters[i])*")"~.(ylabs[i])~"("*%~~%italic("H'")*")"),side=3)
Error: unexpected SPECIAL in
even though the * separator works in other parts of bquote. I can get the right spacing by including the approx. equal symbol directly
mtext(bquote("("*.(letters[i])*")"~.(ylabs[i])~"("*"≈"~italic("H'")*")"),side=3)
but I would like to know if there's a way to get * to work before the plotmath symbol?
I tried this with expression instead of bquote, but couldn't get it to combine the characters with the indexed objects.
The trick is to put the entire text into a subscript:
plot(1:10)
ylabs<-c("All","Native","Exotic")
i=1
b <- bquote(phantom(0)["("*.(letters[i])*")"~.(ylabs[i])~"(" %~~%italic("H'")*")"])
mtext(b, cex = 2, side=3)
I was wondering how I could make the letter "sigma" appear in Greek with the subscript "m" in the text() part of the R code below?:
curve(dnorm(x,175.3,.961),160,190,type="l")
sigmam <- dnorm(177.4,175.3,.961)/ dnorm(177.4,176,4)
text(165,.285,paste("sigmam", "=", round(1/sigmam,digits=2)))
Check out ?plotmath for relevant examples of how to piece this sort of thing together. For instance, here's one adapted from the "## How to combine "math" and numeric variables :"
curve(dnorm(x,175.3,.961),160,190,type="l")
sigmam <- dnorm(177.4,175.3,.961)/ dnorm(177.4,176,4)
text(165,.285, bquote(Sigma[m] == .(round(sigmam,2))))
I'm trying to work out how to have subscript letters in an axis label.
dat <- data.frame(x = rnorm(100), y = rnorm(100))
ggplot(dat, aes(x=x,y=y)) +
geom_point() +
labs(y=expression(Blah[1]))
dat <- data.frame(x = rnorm(100), y = rnorm(100))
ggplot(dat, aes(x=x,y=y)) +
geom_point() +
labs(y=expression(Blah[1d]))
The first example works as it's just a number, as soon as you have a character in the square brackets, it fails. Blah[subscript(1d)] is essentially what I need, but I can't work out how to get it to let me have letters in subscript. I have tried variations, including paste().
The following examples provide strange behavior:
labs(y=expression(Blah[12])) # this works
labs(y=expression(Blah[d])) # this works
labs(y=expression(Blah[d1])) # this works
labs(y=expression(Blah[1d])) # this fails
Thoughts?
The reason the last one fails is that the arguments to expression get run through the R parser and an error is returned when they fail the test of whether they could possibly be correct R syntax. The string or token 1d is not a valid R token (or symbol). It would be possible to either break it into valid R tokens and "connect" with non-space operators, backtick it , or use ordinary quotes. I think either is a better way than using paste:
ggplot(dat, aes(x=x,y=y)) +
geom_point() +
labs(y=expression(Blah[1*d]))
ggplot(dat, aes(x=x,y=y)) +
geom_point() +
labs(y=expression(Blah["1d"]))
Tokens (or "names" or "symbols") in R are not supposed to start with digits. So you get around that limitation by either quoting or by separating 1 and d by a non-space separator, the * operator. That "joins" or "ligates" a pure numeric literal with a legal R symbol or token.
To get a percent sign unsubscripted just:
ggplot(dat, aes(x=x,y=y)) +
geom_point() +
labs(y=expression(Blah[1*d]*"%"))
To put parens around the pct-sign:
expression(Blah[1*d]*"(%)")
The % character has special meaning in R parsing, since it signifies the beginning of a user defined infix operator. So using it as a literal requires that it be quoted. The same reasoning requires that "for" and "in" be quoted, because they are in the "reserved words" group for R. There are other reserved words, (but for and in are the ones that trip me up most often.) Type:
?Reserved
And another "trick" is to use quotation marks around digits within italic()if you need them italicized. Unquoted digits do not get italicized inside that function.
Caveats: paste is a plotmath function except it has different semantics than the base::paste function. In particular, it has no 'sep' argument. So you can never get a space between the printed arguments and if you try to put in a non-space item, a single instance will appear after all the other arguments labeled as sep=" ".
paste0 is not a plotmath function and so will not get interpreted but rather will appear "unprocessed" with its unprocessed arguments inside parentheses.
Okay. I swear I didn't post this just to answer it myself, despite how quickly I got it (always the way when you ask a question!)
Here it is:
ggplot(dat, aes(x=x,y=y)) +
geom_point() +
labs(y=expression(Blah[1][d]))
Thought it best to post the answer rather than remove the question as it may help someone else one day.
'Blahs' aside, what I actually wanted was expression(paste("Hb", A[1][c]," (%)",sep=""))
Why paste0() doesn't work here is beyond me.
How can one concisely change a numeric R variable (keeping it numeric) so that, e.g.,
"-0.34" becomes simply "-.34"?
Only when you output a numeric value do you have to choose a concrete representation (i.e., how the number should be formatted). You cannot change a numeric variable from "-0.34" to "-.34"; both are representations for the same number.
However, when you output an expression e, you can choose how it should be formatted. I don't know of any build-in way to leave off the leading "0", but you could always just remove it manually:
> sub("^(-?)0.", "\\1.", sprintf("%.2f", -0.34))
[1] "-.34"
You can define a function for convenience, e.g.,
numformat <- function(val) { sub("^(-?)0.", "\\1.", sprintf("%.2f", val)) }
In addition to the existing answers, I wanted to mention that the package weights has a function rd() which can be used to "round numbers to text with no leading zero". Of course, the result is not numeric but character.
library("weights")
rd(-0.341, digits=2)
[1] "-.34"
I needed to show numbers to 3 decimal places.
If you want to print to an arbitrary number of decimal places and you don't want to have to add another package (i.e., the weights package above), then this function (adapted from #stefan's answer) seems to work:
numformat <- function(x, digits = 2) {
ncode <- paste0("%.", digits, "f")
sub("^(-?)0.", "\\1.", sprintf(ncode, x))
}
So for example:
> numformat(-.232, 2)
[1] "-.23"
> numformat(-.232, 3)
[1] "-.232"
> numformat(-.232, 4)
[1] "-.2320"
In addition to #stefan's nice answer, I stumbled upon the following code which accomplishes the same thing but prints out more decimal places:
f = function(X1)gsub("0\\.","\\.", X1)
If it's for reporting in R Markdown I use the package MOTE with the function apa() and code: apa(-0.34, 2, FALSE) this will return -.34 in my documents.