gpt4 book ai didi

R、ggplot - 共享相同 y 轴但具有不同 x 轴刻度的图形

转载 作者:行者123 更新时间:2023-12-01 17:00:14 34 4
gpt4 key购买 nike

上下文

我有一些数据集/变量,我想绘制它们,但我想以紧凑的方式做到这一点。为此,我希望它们共享相同的 y 轴但不同的 x 轴,并且由于分布不同,我希望其中一个 x 轴进行对数缩放,另一个进行线性缩放。

示例

假设我有一个长尾变量(我希望 x 轴在绘制时按对数缩放):

library(PtProcess)
library(ggplot2)

set.seed(1)
lambda <- 1.5
a <- 1
pareto <- rpareto(1000,lambda=lambda,a=a)
x_pareto <- seq(from=min(pareto),to=max(pareto),length=1000)
y_pareto <- 1-ppareto(x_pareto,lambda,a)
df1 <- data.frame(x=x_pareto,cdf=y_pareto)

ggplot(df1,aes(x=x,y=cdf)) + geom_line() + scale_x_log10()

Long tail

和一个普通变量:

set.seed(1)
mean <- 3
norm <- rnorm(1000,mean=mean)
x_norm <- seq(from=min(norm),to=max(norm),length=1000)
y_norm <- pnorm(x_norm,mean=mean)
df2 <- data.frame(x=x_norm,cdf=y_norm)

ggplot(df2,aes(x=x,y=cdf)) + geom_line()

Normal

我想使用相同的 y 轴并排绘制它们。

尝试#1

我可以用小平面来做到这一点,这看起来很棒,但我不知道如何使每个 x 轴具有不同的比例(scale_x_log10() 使它们都对数缩放):

df1 <- cbind(df1,"pareto")
colnames(df1)[3] <- 'var'
df2 <- cbind(df2,"norm")
colnames(df2)[3] <- 'var'
df <- rbind(df1,df2)

ggplot(df,aes(x=x,y=cdf)) + geom_line() +
facet_wrap(~var,scales="free_x") + scale_x_log10()

Facets attempt

尝试#2

使用grid.arrange,但我不知道如何保持两个绘图区域具有相同的纵横比:

library(gridExtra)
p1 <- ggplot(df1,aes(x=x,y=cdf)) + geom_line() + scale_x_log10() +
theme(plot.margin = unit(c(0,0,0,0), "lines"),
plot.background = element_blank()) +
ggtitle("pareto")
p2 <- ggplot(df2,aes(x=x,y=cdf)) + geom_line() +
theme(axis.text.y = element_blank(),
axis.ticks.y = element_blank(),
axis.title.y = element_blank(),
plot.margin = unit(c(0,0,0,0), "lines"),
plot.background = element_blank()) +
ggtitle("norm")
grid.arrange(p1,p2,ncol=2)

Grid attempt

PS:图的数量可能会有所不同,因此我不是在寻找专门针对 2 个图的答案

最佳答案

扩展您的尝试#2,gtable 或许能够帮助您。如果两个图表中的边距相同,则两个图中唯一变化的宽度(我认为)是 y 轴刻度线标签和轴文本占用的空间,这反过来又改变了面板的宽度。使用 here 中的代码,轴文本占用的空间应该相同,因此两个面板区域的宽度应该相同,因此长宽比也应该相同。然而,结果(右侧没有边距)看起来并不漂亮。所以我在 p2 的右侧添加了一点边距,然后在 p2 的左侧去掉了相同的边距。对于 p1 也是如此:我在左侧添加了一点,但在右侧删除了相同的数量。

library(PtProcess)
library(ggplot2)
library(gtable)
library(grid)
library(gridExtra)

set.seed(1)
lambda <- 1.5
a <- 1
pareto <- rpareto(1000,lambda=lambda,a=a)
x_pareto <- seq(from=min(pareto),to=max(pareto),length=1000)
y_pareto <- 1-ppareto(x_pareto,lambda,a)
df1 <- data.frame(x=x_pareto,cdf=y_pareto)

set.seed(1)
mean <- 3
norm <- rnorm(1000,mean=mean)
x_norm <- seq(from=min(norm),to=max(norm),length=1000)
y_norm <- pnorm(x_norm,mean=mean)
df2 <- data.frame(x=x_norm,cdf=y_norm)

p1 <- ggplot(df1,aes(x=x,y=cdf)) + geom_line() + scale_x_log10() +
theme(plot.margin = unit(c(0,-.5,0,.5), "lines"),
plot.background = element_blank()) +
ggtitle("pareto")
p2 <- ggplot(df2,aes(x=x,y=cdf)) + geom_line() +
theme(axis.text.y = element_blank(),
axis.ticks.y = element_blank(),
axis.title.y = element_blank(),
plot.margin = unit(c(0,1,0,-1), "lines"),
plot.background = element_blank()) +
ggtitle("norm")

gt1 <- ggplotGrob(p1)
gt2 <- ggplotGrob(p2)

newWidth = unit.pmax(gt1$widths[2:3], gt2$widths[2:3])

gt1$widths[2:3] = as.list(newWidth)
gt2$widths[2:3] = as.list(newWidth)

grid.arrange(gt1, gt2, ncol=2)

enter image description here

编辑要在右侧添加第三个绘图,我们需要对绘图 Canvas 进行更多控制。一种解决方案是创建一个新的 gtable,其中包含用于三个图的空间和用于右边距的附加空间。在这里,我让图中的边距来处理图之间的间距。

p1 <- ggplot(df1,aes(x=x,y=cdf)) + geom_line() + scale_x_log10() +
theme(plot.margin = unit(c(0,-2,0,0), "lines"),
plot.background = element_blank()) +
ggtitle("pareto")
p2 <- ggplot(df2,aes(x=x,y=cdf)) + geom_line() +
theme(axis.text.y = element_blank(),
axis.ticks.y = element_blank(),
axis.title.y = element_blank(),
plot.margin = unit(c(0,-2,0,0), "lines"),
plot.background = element_blank()) +
ggtitle("norm")

gt1 <- ggplotGrob(p1)
gt2 <- ggplotGrob(p2)

newWidth = unit.pmax(gt1$widths[2:3], gt2$widths[2:3])

gt1$widths[2:3] = as.list(newWidth)
gt2$widths[2:3] = as.list(newWidth)

# New gtable with space for the three plots plus a right-hand margin
gt = gtable(widths = unit(c(1, 1, 1, .3), "null"), height = unit(1, "null"))

# Instert gt1, gt2 and gt2 into the new gtable
gt <- gtable_add_grob(gt, gt1, 1, 1)
gt <- gtable_add_grob(gt, gt2, 1, 2)
gt <- gtable_add_grob(gt, gt2, 1, 3)

grid.newpage()
grid.draw(gt)

enter image description here

关于R、ggplot - 共享相同 y 轴但具有不同 x 轴刻度的图形,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/14743060/

34 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com