You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

ggplot2中geom_hex()为何未使用完整颜色刻度?

问题:geom_hex() 颜色映射不符合预期

环境

  • R 版本:3.6.0
  • {ggplot2} 版本:3.4.0

复现代码

library(ggplot2)
library(cowplot)
library(hexbin)

df <- data.frame(x = rnorm(1000), y = rnorm(1000))

plot_grid(
  ggplot(df) + geom_bin_2d(aes(x = x, y = y)),
  ggplot(df) + geom_hex(aes(x = x, y = y)),
  labels = c("bin", "hex"),
  label_size = 12
)

问题现象

两个图表的图例数值范围一致(0至约12.5),颜色映射为深蓝到浅蓝:

  • geom_bin_2d() 图表中间为浅蓝、外围为深蓝,符合正态分布的预期;
  • geom_hex() 图表几乎全为深蓝,无明显浅蓝区域,仅存在少量颜色变化。

手动用hexbin()验证计数范围正常:

> summary(hexbin(df$x, df$y))
'hexbin' object from call: hexbin(x = df$x, y = df$y) 
n = 1000  points in nc = 351  hexagon cells in grid dimensions  36 by 31 
      cell            count             xcm                ycm          
 Min.   :  18.0   Min.   : 1.000   Min.   :-3.54600   Min.   :-3.06479  
 1st Qu.: 389.5   1st Qu.: 1.000   1st Qu.:-0.91158   1st Qu.:-0.92188  
 Median : 565.0   Median : 2.000   Median : 0.02048   Median : 0.07285  
 Mean   : 559.9   Mean   : 2.849   Mean   : 0.04781   Mean   : 0.03474  
 3rd Qu.: 726.5   3rd Qu.: 4.000   3rd Qu.: 0.98753   3rd Qu.: 0.98776  
 Max.   :1098.0   Max.   :12.000   Max.   : 4.50242   Max.   : 3.02475 

请问为何geom_hex()没有正确将计数映射至fill美学?


解决方案

问题根源

geom_bin_2d() 和 geom_hex() 在ggplot2 3.4.0中默认使用的颜色比例尺不一致:

  • geom_bin_2d() 自动使用 viridis 连续色阶(scale_fill_viridis_c()),该色阶的高值(高计数)对应明亮的浅色调,视觉对比度高,高计数区域更显眼;
  • geom_hex() 默认仍使用传统的连续渐变色阶(scale_fill_continuous()),颜色对比度较低,且由于六边形分箱的特性,高计数的六边形数量少、面积小,导致浅色调区域不明显,整体看起来偏深蓝。

同时两者分箱逻辑存在差异:geom_bin_2d() 默认30×30的矩形分箱,高计数单元更密集,视觉上浅蓝区域更大;而geom_hex() 的六边形分箱单元数量更少(示例中为351个),高计数单元更集中,视觉占比小。

修复方法

方法1:统一颜色比例尺

给geom_hex()添加和geom_bin_2d()一致的viridis色阶,提升高值区域辨识度:

plot_grid(
  ggplot(df) + geom_bin_2d(aes(x = x, y = y)),
  ggplot(df) + geom_hex(aes(x = x, y = y)) + scale_fill_viridis_c(),
  labels = c("bin", "hex"),
  label_size = 12
)

方法2:调整分箱数量

增加geom_hex()的bins参数,让分箱更细密,高计数区域更分散:

plot_grid(
  ggplot(df) + geom_bin_2d(aes(x = x, y = y)),
  ggplot(df) + geom_hex(aes(x = x, y = y), bins = 50) + scale_fill_viridis_c(),
  labels = c("bin", "hex"),
  label_size = 12
)

方法3:自定义颜色渐变

如果偏好传统配色,可手动调整颜色对比度:

plot_grid(
  ggplot(df) + geom_bin_2d(aes(x = x, y = y)),
  ggplot(df) + geom_hex(aes(x = x, y = y)) + 
    scale_fill_gradient(low = "#001f3f", high = "#7fdbff"),
  labels = c("bin", "hex"),
  label_size = 12
)

验证

修改后,geom_hex()的颜色映射会和geom_bin_2d()一致,中间高计数区域显示浅蓝,外围低计数区域显示深蓝,符合正态分布预期。


内容的提问来源于stack exchange,提问作者Michael Henry

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.05 21:25:16