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

如何用Base R绘制含日期、分组和频次的堆叠条形图?

问题描述

我有一个包含Date、Title、Units字段的数据集,想用Base R绘制堆叠条形图(只需实现图示原理,无需关注配色等细节)。执行barplot(Units ~ Title, obp)时出现错误:

Error in barplot.formula(Units ~ Title, obp) : duplicated categorical values - try another formula or subset

求解决方法(禁止使用ggplot2)。示例数据如下:

obp <- structure(list(Date = structure(c(19679, 19680, 19684, 19688, 
19689, 19698, 19746, 19747, 19749, 19750, 19752, 19753, 19753, 
19756, 19764, 19767, 19770, 19778, 19782, 19782, 19790, 19793, 
19795, 19800, 19802, 19803, 19803, 19803, 19804, 19805, 19805, 
19805, 19807, 19809, 19809, 19809, 19810, 19812, 19815, 19816, 
19821, 19828, 19829, 19829, 19831, 19831, 19835, 19836, 19837, 
19838, 19839, 19840, 19842, 19848, 19849, 19850, 19851, 19854, 
19855, 19856, 19858, 19858, 19859, 19860, 19862, 19865, 19868, 
19870, 19871, 19871, 19872, 19877, 19878, 19878, 19883, 19884, 
19884, 19886, 19891, 19891), class = "Date"), Title = structure(c(3L, 
3L, 3L, 3L, 3L, 3L, 1L, 1L, 1L, 1L, 1L, 3L, 1L, 1L, 1L, 1L, 1L, 
2L, 3L, 2L, 2L, 1L, 1L, 1L, 4L, 1L, 4L, 2L, 4L, 1L, 4L, 2L, 4L, 
1L, 4L, 2L, 4L, 4L, 4L, 4L, 4L, 4L, 4L, 4L, 4L, 2L, 4L, 4L, 4L, 
4L, 4L, 4L, 1L, 4L, 4L, 4L, 2L, 4L, 2L, 4L, 1L, 4L, 1L, 4L, 2L, 
4L, 4L, 4L, 4L, 4L, 4L, 4L, 4L, 4L, 4L, 1L, 4L, 4L, 1L, 4L), levels = c("A", 
"D", "L", "C"), class = "factor"), Units = c(2L, 1L, 1L, 2L, 
1L, 1L, 1L, 1L, 1L, 3L, 1L, 1L, 1L, 2L, 1L, 1L, 1L, 2L, 1L, 1L, 
1L, 1L, 1L, 1L, 1L, 1L, 1L, 1L, 2L, 1L, 1L, 1L, 1L, 1L, 1L, 1L, 
1L, 1L, 1L, 1L, 1L, 2L, 1L, 1L, 2L, 1L, 1L, 1L, 1L, 1L, 1L, 1L, 
1L, 1L, 1L, 2L, 1L, 1L, 1L, 1L, 1L, 1L, 1L, 3L, 2L, 1L, 1L, 1L, 
1L, 1L, 1L, 1L, 1L, 1L, 1L, 1L, 1L, 1L, 1L, 2L)), class = "data.frame", row.names = c(NA, 
-80L))
报错原因

barplot.formula要求每个分类变量组合对应唯一的数值,但你的数据中同一个Title对应多条Units记录(比如多个Date对应同一个Title),函数无法自动聚合重复值,因此报错。

解决方法

需要先按Date和Title分组汇总Units的总和,将数据转换为适合barplot的矩阵格式,再绘制堆叠条形图。以下是两种可行方案:

方案一:使用xtabs快速生成交叉表

# 按Date和Title汇总Units总和,生成交叉表
units_table <- xtabs(Units ~ Date + Title, data = obp)

# 绘制堆叠条形图,legend.text显示Title类别
barplot(units_table, legend.text = colnames(units_table), main = "按日期分组的Title堆叠条形图")

方案二:使用aggregate+reshape整理数据

# 按Date和Title分组,计算Units总和
agg_data <- aggregate(Units ~ Date + Title, data = obp, sum)

# 将长格式数据转换为宽格式(每个Date一行,每个Title一列)
wide_data <- reshape(agg_data, idvar = "Date", timevar = "Title", direction = "wide")

# 把缺失值替换为0(避免绘图时出错)
wide_data[is.na(wide_data)] <- 0

# 提取数值矩阵,行名为Date
plot_matrix <- as.matrix(wide_data[, -1])
rownames(plot_matrix) <- wide_data$Date

# 绘制堆叠条形图,清理列名作为图例
barplot(plot_matrix, legend.text = gsub("Units\\.", "", colnames(plot_matrix)))

两种方案都能生成堆叠条形图,其中每个条形代表一个Date,条形的不同部分对应该日期下各Title的Units总和。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.22 02:17:05