ggplot2中的geoms和stats有什么区别?

23

在R包ggplot2中,几何物体(geoms)和统计变换(stats)都可以用于绘制图形,并且它们经常给出类似的结果(例如,geom_area和stat_bin)。它们通常也有略微不同的参数,例如在二维密度图中:

geom_density_2d(mapping = NULL, data = NULL, stat = "density2d",
  position = "identity", ..., lineend = "butt", linejoin = "round",
  linemitre = 1, na.rm = FALSE, show.legend = NA, inherit.aes = TRUE)

stat_density_2d(mapping = NULL, data = NULL, geom = "density_2d",
  position = "identity", ..., contour = TRUE, n = 100, h = NULL, na.rm =
  FALSE, show.legend = NA, inherit.aes = TRUE)

这两种类型的对象有根本性的区别吗?

3个回答

54
这只是对已接受答案的补充。
根据 ggplot2 的作者 Hadley Wickkam 在他的书《ggplot2: Elegant Graphics for Data Analysis》第 5.2 节“逐层构建绘图”中所说,链接在此(link here),只需要设置 stat 和 geom 中的一个:每个 geom 都有一个默认的 stat,每个 stat 都有一个默认的 geom。请注意,不要删除 HTML 标记。
上面的被接受的答案解释得很好为什么它们不同。这是为了解释为什么在实践中难以区分它们--每当您使用一个geom层,您也会隐含地使用一个stat层(即使它只是身份转换); 同样,每当您使用一个stat层时,您也会隐含地使用一个geom层。如果您满意任何一层使用的默认值,那么明确指出两层将是多余的。即使您对任一层提供的默认值不满意,您也可以将其作为参数修改每个层(即您可以修改默认的geom作为参数传递给任何stat_*函数,并且您可以修改默认的stat作为参数传递给任何geom_*函数)。用Hadley Wickham的话来说(与上面相同的来源):

您可以在...中传递参数(在这种情况下,stat和geom参数会自动分开)

这个概念在概念上有些难以理解,这也是我一直有这个问题的原因。在他关于ggplot2底层哲学的论文中,在此处找到第4节,“默认层次结构”中,Hadley Wickham解释了这种默认行为背后的实际考虑,即简化代码,否则代码会变得不必要地冗长。
例如,如果没有默认规范,并仅使用图形语法,一个简单散点图的代码可能如下所示:
ggplot() +
layer(
data = diamonds, mapping = aes(x = carat, y = price),
geom = "point", stat = "identity", position = "identity"
) +
scale_y_continuous() +
scale_x_continuous() +
coord_cartesian()

使用默认的比例尺和坐标,我们可以这样编写代码:

ggplot(data = Diamonds, aes(x = carat, y = price)) + 
layer(
geom = "point", stat = "identity", position = "identity"
)

但是这段代码仍然太长了,因为statposition的值只是"identity",这基本上意味着什么都不做,所以为什么要明确地写出来呢?

然而,layer()函数没有statposition的默认值 - 它们需要在调用layer()函数时显式指定。

为了解决这个问题,Hadley 将geom_*函数和stat_*函数作为包装器添加到layer()函数中,这些函数对于geomstat参数都有默认值。stat_*geom_*函数之间的区别在于哪个参数具有不可变(不可更改)的默认值,即statgeom

来源: http://ggplot2.tidyverse.org/reference/layer.html

所以对于geom_*函数,您可以更改stat参数的默认值,但无法更改geom参数的默认值,而对于stat_*函数,您可以更改geom参数的默认值,但无法更改stat参数的默认值。

图层是数据、统计和几何体的组合,可能包含位置调整。通常使用geom_*stat_*调用创建层,但也可以直接使用此函数[layer()函数]创建。


8
非常感谢你解释了stat_*geom_*函数实际上是提供了layer()函数的合理默认值包装器。对我来说,这是你回答中最令人瞪大眼睛的部分。我的学生们(间接地)非常感激你 :-) - András Aszódi
我坚信 Hadley Wickham 故意设计了扭曲和令人困惑的界面,强迫人们购买他的书籍才能理解如何使用他的库。 - Stefano Borini

23

geoms代表"几何对象"。这些是图形上看到的核心元素,例如点、线、区域、曲线等。

stats代表"统计变换"。这些对象以不同方式总结数据,如计算观察值的数量、创建最符合数据的loess线,或向loess线添加置信区间。

由于geoms是绘图的"核心",所以这些是必要的对象。另一方面,stats不是产生绘图所必需的,但可以极大地增强最终绘图的效果。

正如@eipi10在评论中所指出的那样,这些区别在某种程度上是概念性的,因为大多数geoms在绘制之前都经历了一些统计变换。其中包括geom_bargeom_smoothgeom_quantile。一些常见的例外情况是数据以更多或更少的"原始"形式呈现的geom_pointgeom_line以及较少使用的geom_rug


10
据我所知,统计量和几何图形总是一起使用的,但每个几何图形都有一个默认的统计量。因此,您不必显式指定统计量,但仍需要使用统计量。如果您查看 ggplot 帮助文档,您可以看到每种几何图形的默认统计量。您也可以反过来,在 stat_xxx() 的调用中指定一个 geom。大多数情况下,您不必担心这些细节,但了解它们很好,以防您想修改默认行为。 - eipi10
8
geom_bar 中,最常见的情况是默认计算行数(geom_bar 的默认统计量为 stat_count)。因此,如果您的数据已经被汇总,您需要指定 stat="identity",表示不对原始数据进行任何转换。 - eipi10
3
谢谢提供链接,我会添加一条注释,以便更好地涵盖这种情感。 - lmo
@eipi10上面评论的ggplot_help链接对我没用。我猜这是预期的页面https://ggplot2.tidyverse.org/reference/,对我确实有帮助! - ciaran haines
很高兴能帮上忙。看起来,我4.5年前在评论中留下的链接已经失效了。感谢你发布了最新的链接。 - eipi10

1

geom是用于几何表示的,而stat则是用于统计信息和表示的。我认为有时候geom会使用一些统计函数,例如stat_count()geom_bar()使用。在这种情况下,geom_bar需要一个参数(x或y),而stat_count负责计算频率。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接