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

scale_fill_gradient2颜色未达设定上限:数据超限时颜色偏浅问题

问题:热图中接近/超出上限的数值颜色未显示为指定高值颜色

尝试用热图展示偏离0的数值,但发现接近或超出上限4的数值对应的颜色远浅于指定的高值颜色#276419。

原始代码

library(ggplot2)

genotype <- c(rep(c("A", "B"), times = 8))
gene <- rep(c("g1", "g2", "g3", "g4", "g5", "g6", "g7", "g8"),
            times = 2)
response <- c(-0.3026690, -2.5850300, -4.9285293, -7.5158563,
              2.2674635, -0.2312305, 3.7952988, -1.5507423,
              4.2041790, 1.1214478,  0.4004754, -1.9283537,
              2.1161335, -7.0709069, 2.8636382, -0.1685422)
d <- data.frame(genotype, gene, response)

ggplot(d, aes(x = genotype, y = gene, fill = response)) +
  geom_tile() +
  scale_fill_gradient2(low = "#8E0152", mid = "#F7F7F7", high = "#276419", 
                       limits=c(-7, 4), midpoint = 0, oob = scales::squish) 

问题表现

颜色偏浅的热图

原因分析

scale_fill_gradient2会将midpoint到high的数值范围(此处为0到4)线性映射为mid到high的颜色渐变。即使使用oob = scales::squish将超出上限的数值压缩到4,颜色仍会基于压缩后的数值在渐变区间内的位置计算——接近4的数值(如3.795)虽理论上应接近深绿,但视觉上可能因渐变逻辑显得偏浅;而被压缩到4的数值(如4.204)未显示为指定深绿,是因为渐变函数在边界处的映射特性。

解决方案

以下两种方法可让所有>=4的数值直接显示为指定深绿色:

方法1:手动截断数值

先将超出限制范围的数值替换为边界值,再用于绘图:

# 截断数值到[-7,4]区间
d$response_clamped <- pmax(pmin(d$response, 4), -7)

ggplot(d, aes(x = genotype, y = gene, fill = response_clamped)) +
  geom_tile() +
  scale_fill_gradient2(low = "#8E0152", mid = "#F7F7F7", high = "#276419", 
                       limits=c(-7, 4), midpoint = 0)

方法2:使用scale_fill_gradientn自定义颜色断点

通过手动指定颜色对应的数值断点,确保>=4的数值直接映射到深绿色:

ggplot(d, aes(x = genotype, y = gene, fill = response)) +
  geom_tile() +
  scale_fill_gradientn(
    colors = c("#8E0152", "#F7F7F7", "#276419"),
    values = scales::rescale(c(-7, 0, 4)),  # 对应数值的相对映射位置
    limits = c(-7, 4),
    oob = scales::squish
  )

修改后,所有接近或超出上限4的数值都会显示为指定的深绿色#276419,符合预期。

内容的提问来源于stack exchange,提问作者Adam L.

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.20 16:58:16