副轴/双轴-ggplot [英] Secondary / Dual axis - ggplot
问题描述
我提出这个问题的原因有三个:首先,使用ggplot重新开始双轴讨论.第二,询问是否有不折不扣的通用方法可以做到这一点.最后,就变通办法寻求您的帮助.
I am opening this question for three reasons : First, to re-open the dual-axis discussion with ggplot. Second, to ask if there is a non-torturing generic approach to do that. And finally to ask for your help with respect to a work-around.
我意识到,关于如何向ggplot中添加辅助轴有很多讨论和问题.这些通常会得出以下两个结论之一:
I realize that there are multiple discussions and questions on how to add a secondary axis to a ggplot. Those usually end up in one of two conclusions:
-
这很糟糕,不要这样做:Hadley Wickham回答了相同的问题.
It's bad, don't do it: Hadley Wickham answered the same question here, concluding that it is not possible. He had a very good argument that "using separate y scales (not y-scales that are transformations of each other) are fundamentally flawed".
If you insist, over-complicate your life and use grids : for example here and here
但是,这是我经常遇到的一些情况,在这种情况下,可视化将大大受益于双轴.我抽象了以下概念.
However, here are some situations that I often face, in which the visualization would greatly benefit from dual-axis. I abstracted the concepts below.
-
图很宽,因此复制在右侧的y轴会有所帮助(或在顶部的x轴)会简化解释. (我们都偶然发现了其中一个需要在屏幕上使用标尺的图,因为轴太远了)
The plot is wide, hence duplicating the y-axis on the right side would help (or x-axis on the top) would ease interpretation. (We've all stumbled across one of those plots where we need to use a ruler on the screen, because the axis is too far)
我需要在原始轴上添加一个新的轴,该轴是变换(例如:百分比,分位数,..). (我目前对此有疑问.下面的可重现示例)
I need to add a new axis that is a transformation to the original axes (eg: percentages, quantiles, .. ). (I am currently facing a problem with that. Reproducible example below)
最后,添加分组/元信息:当我将分类数据与多级一起使用时,我偶然发现了这一点(例如:Categories = {1,2,x, y,z},它们被元分解"为字母和数字.)即使对元级别进行颜色编码并添加图例甚至是构面也可以解决问题,但是使用辅助轴,用户无需将条形的颜色与图例的颜色进行匹配.
And finally, adding Grouping/Meta information: I stumble across that when using categorical data with multiple-level, (e.g.: Categories = {1,2,x,y,z}, which are "meta-divided" into letters and numerics.) Even though color-coding the meta-levels and adding a legend or even facetting solve the issue, things get a little bit simpler with a secondary axis, where the user won't need to match the color of the bars to that of the legend.
General question: Given the new extensibility features ggplot 2.0.0, is there a more-robust no-torture way to have dual-axis without using grids?
最后一条评论:我绝对同意错误地使用双轴可能会产生误导性的危险……但是,对于信息可视化和数据科学而言,不是一般情况吗?
And one final comment: I absolutely agree that the wrong use of dual-axis can be dangerously misleading... But, isn't that the case for information visualization and data science in general?
解决方法问题:
当前,我需要一个百分比轴(第二种情况).我使用annotate
和geom_hline
作为解决方法.但是,我不能将文本移到主图之外. hjust
似乎也没有和我一起工作.
Currently, I need to have a percentage-axis (2nd case). I used annotate
and geom_hline
as a workaround. However, I can't move the text outside the main plot. hjust
also didn't seem to work with me.
可复制的示例:
library(ggplot2)
# Random values generation - with some manipulation :
maxVal = 500
value = sample(1:maxVal, size = 100, replace = T)
value[value < 400] = value[value < 400] * 0.2
value[value > 400] = value[value > 400] * 0.9
# Data Frame prepartion :
labels = paste0(sample(letters[1:3], replace = T, size = length(value)), as.character(1:length(value)))
df = data.frame(sample = factor(labels, levels = labels), value = sort(value, decreasing = T))
# Plotting : Adding Percentages/Quantiles as lines
ggplot(data = df, aes(x = sample, y = value)) +
geom_bar(stat = "identity", fill = "grey90", aes(y = maxVal )) +
geom_bar(stat = "identity", fill = "#00bbd4") +
geom_hline(yintercept = c(0, maxVal)) + # Min and max values
geom_hline(yintercept = c(maxVal*0.25, maxVal*0.5, maxVal*0.75), alpha = 0.2) + # Marking the 25%, 50% and 75% values
annotate(geom = "text", x = rep(100,3), y = c(maxVal*0.25, maxVal*0.5, maxVal*0.75),
label = c("25%", "50%", "75%"), vjust = 0, hjust = 0.2) +
theme(axis.text.x = element_text(angle = 90, hjust = 1)) +
theme(panel.background = element_blank()) +
theme(plot.background = element_blank()) +
theme(plot.margin = unit(rep(2,4), units = "lines"))
推荐答案
响应#1
我们都偶然发现了其中一个需要在屏幕上使用标尺的绘图中的一个,因为轴太远了
cowplot .
# Assign your original plot to some variable, `gpv` <- ggplot( ... )
ggdraw(switch_axis_position(gpv, axis="y", keep="y"))
这篇关于副轴/双轴-ggplot的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!