可以将文章内容翻译成中文,广告屏蔽插件可能会导致该功能失效(如失效,请关闭广告屏蔽插件后再试):
问题:
I am using the dot function to format text labels in a plot created with ggplot2
. This works fine when using aes
, but doesn't work like expected when using aes_string
. Is there a workaround to make it work with aes_string
?
require(ggplot2) # Define the format function dot <- function(x, ...) { format(x, ..., big.mark = ".", scientific = FALSE, trim = TRUE) } # Create dummy data df <- data.frame(cbind(levels(iris$Species),c(10000000000,200000,30000))) df$X2 <- as.numeric(as.character(df$X2)) # Works with aes ggplot(iris) + geom_bar(aes(Species,Sepal.Width),stat="identity") + geom_text(data=df,aes(x=factor(X1),y=180,label=dot(X2))) # Doesn't work with aes_string ggplot(iris) + geom_bar(aes(Species,Sepal.Width),stat="identity") + geom_text(data=df,aes_string(x="X1",y=180,label=dot("X2")))
回答1:
Rather than just quote "X2", you must quote the whole expression
ggplot(iris) + geom_bar(aes(Species, Sepal.Width), stat = "identity") + geom_text(data=df, aes_string(x="X1", y =180, label = "dot(X2)"))
If you wanted to specify variable names via a character vector, you would use paste()
to build that expression.
回答2:
You're passing a string constant to dot
and dot("X2")
returns "X2"
. So you're basically giving aes_string
the argument label = "X2"
.
I got this to work
ggplot(iris) + geom_bar(aes(Species, Sepal.Width), stat = "identity") + geom_text(data=df, aes_string(x="X1", y =180, label = deparse(dot(df$X2))))
Edit
As suggested by MrFlick, you could also use df[,"X2"]
if you need to pass the column name as a string. I.e.
ggplot(iris) + geom_bar(aes(Species, Sepal.Width), stat = "identity") + geom_text(data=df, aes_string(x="X1", y =180, label = deparse(dot(df[,"X2"]))))
回答3:
As implied by my comment, I dislike relying on deparse
or other evaluation tricks unless I have to:
col <- "X2" new_col <- paste0(col,"_dot") df[,new_col] <- dot(df[,col]) ggplot(iris) + geom_bar(aes(Species,Sepal.Width),stat="identity") + geom_text(data=df,aes_string(x="X1",y=180,label=new_col))
I presented this version as if we were writing code in a function and had received the "X2"
as an argument.