如何绘制分类、累积时间相关数据?实现右侧起始的翻转瀑布图
问题
我有一组非递减、右连续的时间相关数据,每条数据都关联可重复的分类信息。我想绘制一种侧翻后从右侧起始的可变宽度条形图/瀑布图,现有Gnuplot脚本生成了累积步数填充图,但我想要实现类似**累积分布函数(CDF)**的效果:曲线左侧数值为0,右侧为最大值;同时把原数据点的标签移至图例,和右侧连续数据分组关联。另外我可以完全控制输入数据,考虑通过逆变换和旋转实现是否更简便?
原Gnuplot脚本:
set term postscript eps enhanced set output "so.eps" $Data <<EOD # date source reg sic pic total 2000-07-25 2000glider C-FJSN 8 0 216 2000-07-28 2000glider C-FJSN 10 0 226 2000-07-28 2000glider C-FJSN 11 0 237 2000-07-28 2000glider C-GCLB 4 0 241 2000-07-29 2000glider C-GCLY 3 0 244 2000-07-29 2000glider C-GCLY 2 0 246 2000-07-29 2000glider C-GCLY 17 0 263 2000-07-30 2000glider C-GCLB 15 0 278 2000-07-30 2000glider C-GCLB 0 13 291 2000-07-30 2000glider C-GCLK 11 0 302 2000-07-30 2000glider C-FJSN 0 16 318 2000-07-30 2000glider C-GCLB 0 10 328 2000-08-02 2000glider C-GQRT 0 13 341 2000-08-04 2000glider C-GCLY 0 11 352 2000-08-05 2000glider C-GCLB 12 0 364 2000-08-05 2000glider C-GCLB 0 12 376 2000-08-06 2000glider C-GCLB 0 11 387 2000-08-07 2000glider C-GFMB 0 12 399 2000-08-07 2000glider C-GCMB 0 11 410 2000-08-08 2000glider C-GCLK 0 12 422 2000-08-09 2000glider C-GCLB 14 0 436 2000-08-09 2000glider C-GCLB 0 9 445 2000-08-10 2000glider C-GCLL 0 10 455 EOD set monochrome set xdata time set timefmt "%Y-%m-%d" set xtics format "%Y-%m-%d" rotate by -30 set ylabel "hours" set grid unset key unset border plot $Data using 1:($6/60) with fillsteps lw 2, \ $Data using 1:($6/60):3 with labels
解决方案
一、对应图表类型
你要的是**反向累积分布函数(Reverse CDF,又称生存函数)**的可视化形式,结合分组分类的填充展示,核心是让数值从右侧最大值向左侧0递减,同时按分类关联图例。
二、Gnuplot实现(无需旋转,直接适配更简便)
因为你能完全控制输入数据,直接计算反向累积值比旋转操作更高效,步骤如下:
预处理数据
- 提取
total列的最大值(示例中为455) - 新增
reverse_total列:reverse_total = 总最大值 - total,实现左侧为0、右侧为最大值的反向累积效果 - 确保同一分类的数据连续,便于分组绘制
- 提取
修改后的Gnuplot脚本
启用图例并按分类映射样式,替换原全局填充逻辑:
set term postscript eps enhanced set output "reverse_cdf.eps" # 定义总累积最大值,也可通过脚本自动提取最后一行的total值 MAX_TOTAL = 455 $Data <<EOD # date source reg sic pic total reverse_total 2000-07-25 2000glider C-FJSN 8 0 216 239 2000-07-28 2000glider C-FJSN 10 0 226 229 2000-07-28 2000glider C-FJSN 11 0 237 218 2000-07-28 2000glider C-GCLB 4 0 241 214 2000-07-29 2000glider C-GCLY 3 0 244 211 2000-07-29 2000glider C-GCLY 2 0 246 209 2000-07-29 2000glider C-GCLY 17 0 263 192 2000-07-30 2000glider C-GCLB 15 0 278 177 2000-07-30 2000glider C-GCLB 0 13 291 164 2000-07-30 2000glider C-GCLK 11 0 302 153 2000-07-30 2000glider C-FJSN 0 16 318 137 2000-07-30 2000glider C-GCLB 0 10 328 127 2000-08-02 2000glider C-GQRT 0 13 341 114 2000-08-04 2000glider C-GCLY 0 11 352 103 2000-08-05 2000glider C-GCLB 12 0 364 91 2000-08-05 2000glider C-GCLB 0 12 376 79 2000-08-06 2000glider C-GCLB 0 11 387 68 2000-08-07 2000glider C-GFMB 0 12 399 56 2000-08-07 2000glider C-GCMB 0 11 410 45 2000-08-08 2000glider C-GCLK 0 12 422 33 2000-08-09 2000glider C-GCLB 14 0 436 19 2000-08-09 2000glider C-GCLB 0 9 445 10 2000-08-10 2000glider C-GCLL 0 10 455 0 EOD set monochrome set xdata time set timefmt "%Y-%m-%d" set xtics format "%Y-%m-%d" rotate by -30 set ylabel "反向累积小时数" set grid set key outside right top # 将图例放在右侧外部,避免遮挡图表 unset border # 遍历所有分类,按分组绘制并生成对应图例 plot for [REG in "C-FJSN C-GCLB C-GCLY C-GCLK C-GQRT C-GFMB C-GCMB C-GCLL"] \ $Data using 1:($7/60)::(strcol(3) eq REG) with fillsteps lw 2 title REG
三、逆变换和旋转的思路分析
如果用旋转方式,步骤是:
- 先绘制常规CDF(左侧0,右侧最大值)
- 通过终端参数(如postscript的
rotate)或set view将图表顺时针旋转90度
但这种方式会导致坐标轴标签、图例文本方向错乱,需要额外调整格式,反而增加复杂度,不推荐使用。
内容的提问来源于stack exchange,提问作者Neil
相关产品推荐
相关产品推荐

