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

使用ggplot绘制基于连续变量的类密度/等高线热力图

实现基于连续变量HPOE的棒球投球等高线热力图

要实现你需要的类密度/等高线热力图,核心是对连续变量HPOE在x-y投球位置网格上进行二维插值,再绘制填充等高线。以下是两种可行方案:

方案一:基于插值的平滑等高线(推荐)

使用akima包对离散投球点的HPOE值做网格插值,得到平滑的连续曲面后,用ggplot2的geom_contour_filled绘制填充等高线,效果最接近目标示例:

library(ggplot2)
library(akima)
library(dplyr)

# 读取数据集
pc_filt <- read.csv("sample_plot_data.csv")

# 对HPOE进行x-y网格插值,生成平滑曲面数据
interp_data <- interp(
  x = pc_filt$x, 
  y = pc_filt$y, 
  z = pc_filt$hpoe,
  nx = 100, ny = 100,  # 数值越高,插值后曲面越平滑
  extrap = TRUE        # 允许在原始数据范围外插值,适配好球区边界
) %>% 
  interp2xyz(data.frame = TRUE) %>% 
  rename(hpoe = z)

# 绘制可视化
ggplot() +
  # 填充等高线图层
  geom_contour_filled(data = interp_data, aes(x = x, y = y, z = hpoe), bins = 15) +
  # 绘制好球区边框
  geom_segment(y = mean(pc_filt$sz_bot), yend = mean(pc_filt$sz_bot), 
               x = -0.89, xend = 0.89, color = "black", size = 1.25) +
  geom_segment(y = mean(pc_filt$sz_top), yend = mean(pc_filt$sz_top), 
               x = -0.89, xend = 0.89, color = "black", size = 1.25) +
  geom_segment(y = mean(pc_filt$sz_bot), yend = mean(pc_filt$sz_top), 
               x = -0.89, xend = -0.89, color = "black", size = 1.25) +
  geom_segment(y = mean(pc_filt$sz_bot), yend = mean(pc_filt$sz_top), 
               x = 0.89, xend = 0.89, color = "black", size = 1.25) +
  # 自定义颜色渐变,可根据需求调整
  scale_fill_viridis_d(option = "plasma", direction = -1) +
  # 保持坐标轴比例一致,还原棒球视角
  coord_equal() +
  labs(x = "横向位置", y = "纵向位置", fill = "HPOE") +
  theme_minimal()

方案二:基于网格汇总的近似等高线

如果不想额外安装akima包,可以用ggplot2内置的stat_summary_2d先对x-y网格内的HPOE做均值汇总,再叠加等高线:

library(ggplot2)

# 读取数据集
pc_filt <- read.csv("sample_plot_data.csv")

ggplot(pc_filt, aes(x = x, y = y, z = hpoe)) +
  # 网格汇总HPOE值,生成热力底图
  stat_summary_2d(aes(fill = ..value..), bins = 50) +
  # 叠加白色等高线,增强轮廓感
  geom_contour(color = "white", size = 0.5) +
  # 绘制好球区边框
  geom_segment(y = mean(pc_filt$sz_bot), yend = mean(pc_filt$sz_bot), 
               x = -0.89, xend = 0.89, color = "black", size = 1.25) +
  geom_segment(y = mean(pc_filt$sz_top), yend = mean(pc_filt$sz_top), 
               x = -0.89, xend = 0.89, color = "black", size = 1.25) +
  geom_segment(y = mean(pc_filt$sz_bot), yend = mean(pc_filt$sz_top), 
               x = -0.89, xend = -0.89, color = "black", size = 1.25) +
  geom_segment(y = mean(pc_filt$sz_bot), yend = mean(pc_filt$sz_top), 
               x = 0.89, xend = 0.89, color = "black", size = 1.25) +
  # 自定义颜色渐变,匹配HPOE的取值范围
  scale_fill_gradient2(low = "blue", mid = "white", high = "red", midpoint = mean(pc_filt$hpoe)) +
  coord_equal() +
  theme_minimal()

为什么之前的方法不符合需求?

  • stat_density2d:仅计算投球点的密度,不支持自定义连续变量z(即HPOE),所以会报错丢弃z美学,其..level..代表密度值而非HPOE,自然无法匹配需求。
  • geom_tile/geom_raster:需要规整的网格数据,原始离散投球点直接使用会出现大量空白或不均匀瓦片,无法形成平滑的热力效果。
  • stat_summary_hex:对六边形网格内的HPOE做均值汇总,属于分块可视化,无法生成示例中的连续平滑等高线。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.17 10:53:22