## ── Attaching core tidyverse packages ──────────────────────── tidyverse 2.0.0 ──
## ✔ dplyr 1.1.4 ✔ readr 2.1.5
## ✔ forcats 1.0.0 ✔ stringr 1.5.1
## ✔ ggplot2 3.5.2 ✔ tibble 3.2.1
## ✔ lubridate 1.9.4 ✔ tidyr 1.3.1
## ✔ purrr 1.0.4
## ── Conflicts ────────────────────────────────────────── tidyverse_conflicts() ──
## ✖ dplyr::filter() masks stats::filter()
## ✖ dplyr::lag() masks stats::lag()
## ℹ Use the conflicted package (<http://conflicted.r-lib.org/>) to force all conflicts to become errors
## Install package "strengejacke" from GitHub (`devtools::install_github("strengejacke/strengejacke")`) to load all sj-packages at once!
##
## Linking to GEOS 3.13.1, GDAL 3.10.2, PROJ 9.5.1; sf_use_s2() is TRUE
##
##
## 载入程序包:'gridExtra'
##
##
## The following object is masked from 'package:dplyr':
##
## combine
##
##
## 载入需要的程序包:grid
Titanic数据集是datasets包的配套案例数据,可以通过as.data.frame将其转化为数据框。解析数据包含哪些变量,如果是分类变量分别有哪些类别?
包含人群分类、性别、年龄、生还情况、频数五个变量,其中分类变量有人群分类有一等舱乘客、二等舱乘客、三等舱乘客和船员四种类别;性别有男性、女性两种类别;年龄有小孩和成年人两种类别;生还情况有是与否两种类别。
data = as.data.frame(Titanic)
DT::datatable(data,rownames = FALSE)
绘制Sex和 Survived的并列条形图和堆叠条形图,并为条形图添加频数标签。
下面代码作了什么数据处理?为什么要这样处理?
选择了性别、生还、人数三个数据,可以更明确的绘制性别和生还的条形图
# 数据准备
df <- data %>% select(Sex,Survived,Freq) %>%
summarise(n=sum(Freq),.by=c(Sex,Survived)) %>%
rename(性别=Sex,生还=Survived,人数=n)
DT::datatable(df,rownames = FALSE)
# 图(a)垂直并列条形图
p1<-ggplot(df,aes(x=性别,y=人数,fill=生还))+
geom_col(width=0.8, # 设置条形宽度
position="dodge", # 绘制并列条形图
color="gray50")+ # 设置条形图的边框颜色
scale_fill_brewer(palette="Set2")+ # 设置填充颜色
geom_text(aes(label=人数),position=position_dodge(0.9),vjust=-0.5,size=3)+ # 设置标签垂直位置和字体大小
ylim(0,1.1*max(df$人数))+ # 设置y轴范围
ggtitle("(a) 垂直并列条形图")
# 图(b) 水平并列条形图
p2<-ggplot(df,aes(x=性别,y=人数,fill=生还))+
geom_col(width=0.7,color="gray50")+ # 绘制堆叠条形图(默认)
geom_text(aes(label=人数),position=position_stack(0.5),size=3)+
scale_fill_brewer(palette="Set2")+
ggtitle("(b) 垂直堆叠条形图")
grid.arrange(p1,p2,ncol=2) # 按2列组合图形
# 图(a)垂直并列条形图
p1<-ggplot(df,aes(x=性别,y=人数,fill=生还))+
geom_col(width=0.8, # 设置条形宽度
position="dodge", # 绘制并列条形图
color="gray50")+ # 设置条形图的边框颜色
scale_fill_brewer(palette="Set2",
labels = c("Yes" = "是", "No" = "否")) +
scale_x_discrete(labels = c("male" = "男性", "female" = "女性")) +
geom_text(aes(label=人数), position=position_dodge(0.9), vjust=-0.5, size=3) +
ylim(0, 1.1*max(df$人数)) +
ggtitle("(a) 垂直并列条形图")
# 图(b) 水平并列条形图
p2<-ggplot(df,aes(x=性别,y=人数,fill=生还))+
geom_col(width=0.7,color="gray50")+ # 绘制堆叠条形图(默认)
geom_text(aes(label=人数),position=position_stack(0.5),size=3)+
scale_fill_brewer(palette="Set2",
labels = c("Yes" = "是", "No" = "否")) +
scale_x_discrete(labels = c("male" = "男性", "female" = "女性")) +
ggtitle("(b) 垂直堆叠条形图")
grid.arrange(p1,p2,ncol=2) # 按2列组合图形
特点:并列条形图(图a)将男性和女性分组并列,每组内按照生还和未生还拆分为两个并排的条形;堆叠条形图(图b)将生还和未生还人数堆叠在同一性别条形上,总高度表示该性别的总人数。
信息:图(a)中男性未生还人数远高于生还人数,图(b)中女性的生还率显著高于男性的生还率。
绘制Class 的帕累托图。
df<-data |>
select(Class,Freq) |>
summarise(n=sum(Freq),.by=Class) |>
rename(乘客舱位=Class,人数=n ) |>
arrange(desc(人数)) |>
mutate(累积百分比 = cumsum(人数*100/sum(人数)), #计算累积百分比
累积百分比 = round(累积百分比,1), #保留一位小数
乘客舱位 = fct_inorder(乘客舱位) #按字符出现顺序定义因子水平
)
datatable(df,rownames = FALSE)
geom_col()+geom_line()+geom_point()等函数作图palette<-rev(brewer.pal(4,"Reds")) # 设置调色板
# 绘制条形图
p<-ggplot(df)+aes(x=乘客舱位,y=人数)+
geom_col(width=0.8,fill=palette,color="grey50")+# 绘制条形图
scale_x_discrete(labels=c("Crew","3rd","1st","2nd"))+ # 将x轴的长标签折行
geom_text(aes(x=乘客舱位,y=人数,label=人数,vjust=-0.5),size=3,color="gray50")+ # 添加数值标签,垂直调整标签位置
ylab("人数\n(人)")+ # 设置y轴标签
theme(axis.text.y=element_text(angle=90,hjust=0.5,vjust=0.5))+ # 调整y轴标签角度
theme(legend.position="none") # 删除图例
# 绘制折线和点
p1<-p+geom_line(aes(x=as.numeric(乘客舱位),y=累积百分比*max(人数/100)))+ # 绘制累积百分比曲线
geom_point(aes(x=as.numeric(乘客舱位),y=累积百分比*max(人数/100)),
size=2.5,shape=23,fill="white")+ # 绘制点
geom_text(aes(label=累积百分比,x=乘客舱位,y=1*累积百分比*max(人数/100),
hjust=0.6,vjust=-0.95),size=3,colour="blue3")+# 添加百分比数值标签
scale_y_continuous(sec.axis = sec_axis(~./max(df$人数/100)))# 添加坐标轴
p1+annotate("text",x=4.3,y=700,label="百分比(%)",angle=90,size=3.5)+
annotate("text",x=3.5,y=900,label="累积百分比曲线",size=3.5)# 添加注释文本
特点:该图形采用双Y轴组合图形式,将柱状图和折线图+散点结合,直观展示了泰坦尼克号不同仓位的乘客分布及其累计占比。
信息:
舱位人数对比
柱状图高度直接反映各舱位的乘客数量差异。例如:
通过排序可直观看出 乘客集中分布的舱位。
累积分布趋势
折线图显示从人数最多的舱位开始,逐步累积的百分比。
生还率潜在关联
若结合生还数据(未在图中显示),可推测:
人数多的舱位(如船员)可能生还率较低。
头等舱人数少但生还比例可能较高。
绘制Class和 Survived 的脊形图。
# 数据准备
df<- data |> select(Class, Survived,Freq) %>%
summarise(人数 = sum(Freq), .by = c(Class,Survived)) %>%
mutate(百分比=人数*100/sum(人数),百分比=round(百分比,1),.by="Class")
datatable(df,rownames = FALSE)
geom_col() 作图ggplot(df)+aes(x=Class,y=百分比,fill=Survived)+ylab("百分比(%)")+
geom_col(width=0.8,color="grey50")+
scale_fill_brewer(palette="Blues")
ggSpine()ggSpine(data=df,aes(x=Class,y=百分比,fill=Survived),stat = 'identity',
palette="Reds",labelsize=3,reverse=TRUE) # 反转调色板颜色
## Warning: The `guide` argument in `scale_*()` cannot be `FALSE`. This was deprecated in
## ggplot2 3.3.4.
## ℹ Please use "none" instead.
## ℹ The deprecated feature was likely used in the ggiraphExtra package.
## Please report the issue to the authors.
## This warning is displayed once every 8 hours.
## Call `lifecycle::last_lifecycle_warnings()` to see where this warning was
## generated.
特点:脊柱图本质:一种宽度可变的堆叠柱状图,宽度通常反映组别样本量
信息:
强调不同舱位中生存/死亡的比例分布,尤其适合展示条件概率(如“给定舱位下的生存率”)。
红色调可能暗示紧急或风险(如死亡比例),但需结合具体业务场景解读。
绘制Class、Sex、Age和Survived4个变量的矩形树状图和旭日图
treemap::treemap()函数作树状图df<-data%>%
rename(人数=Freq) # 将Freq命名为频数
datatable(df,rownames = FALSE)
# 图(a)分层顺序:Class—Sex—Age-Survived
treemap(df,index=c("Class","Sex","Age","Survived"), # 设置聚合索引的列名称
vSize="人数", # 指定矩形大小的列名称
#fontsize.labels=9, # 设置标签字体大小
position.legend="bottom", # 设置图例位置
title="分层顺序:Class—Sex—Age-Survived")
sunburstR::sunburst() 函数作旭日图d3r::d3_nest将数据框转化为层次数据“d3.js”作为绘图输入df_tree<-d3_nest(df,value_cols="人数") # 将数据框转换为“d3.js”层次结构
datatable(df,rownames = FALSE)
sunburst(data=df_tree, # 绘制旭日图
valueField="人数", # 计算大小字段的字符为vSize
count=TRUE, # 在解释中包括计数和总数
sumNodes=TRUE) # 默认总和节点=TRUE
树状图特点:
分层结构:
按 Class → Sex → Age → Survived
顺序嵌套,每个层级用矩形块表示。
矩形面积大小由 人数
决定,直观反映各组频数。
视觉编码:
颜色默认按分类变量自动分配,区分不同组别(如不同舱位、性别)。
标签显示最内层分组(如 Survived 的
Yes/No)。
交互性:
plotly
扩展)显示详细数据。传达信息:
展示多维分类变量(舱位、性别、年龄、生存状态)的组合分布。
突出主要人群(如面积最大的矩形代表“3等舱男性成年未生存”)。
适合快速识别高频组合和异常值(如极小矩形可能对应罕见情况)。
旭日图特点:
环形层级结构:
中心圆为根节点(总人数),外层环依次对应
Class → Sex → Age → Survived。
扇形角度和半径由 人数 决定,面积=频数。
交互功能:
点击扇形可下钻(查看子层级)或上卷(返回父层级)。
悬停显示具体数值和占比(如 count=TRUE
启用的计数标签)。
颜色与标签:
Male/Female)。传达信息:
直观呈现数据的层级占比(如“1等舱女性生存者占全体比例”)。
强调数据流动和层级关系(比树形图更清晰展示父子结构)。
适合展示比例构成和路径分析(如“从舱位到生存状态的逐层分布”)。
绘制Class和Survived 的点阵图、热图和南丁格尔玫瑰图。
df<-data%>%
summarise(人数=sum(Freq),.by=c(Class,Survived))
# 图(a)Class和Survived的点阵图
palette<-rev(brewer.pal(11,"RdYlGn")) # 设置调色板
ggballoonplot(df,x="Class",y="Survived", # 设置图形的x轴和y轴
shape=21, # 设置形状,默认21,可选22,23,24,25
size="人数",fill="人数", # 设置点的大小和填充颜色变量
size.range = c(7,15), # 设置最小点和最大点的范围
rotate.x.text=FALSE, # x轴文本标签不旋转
ggtheme=scale_fill_gradientn(colors=palette))+ # 设置渐变颜色
theme(axis.text.y=element_text(angle=90))+ # y轴标签旋转90度
ggtitle("(a) Class和Survived的点阵图")
ggiraphExtra::ggHeatmap()作热力图分别作矩形热图和极坐标热图
df <- data %>%
group_by(Class, Survived) %>%
summarise(人数 = sum(Freq), .groups = "drop")
ggHeatmap(df,aes(x=Class,y=Survived,fill=人数), # 绘制矩形热图
addlabel=TRUE, # 添加数值标签
palette="Reds")+ # 使用红色调色板
ggtitle("(a1) 矩形热图") # 添加标题
## Scale for x is already present.
## Adding another scale for x, which will replace the existing scale.
## Scale for y is already present.
## Adding another scale for y, which will replace the existing scale.
ggiraphExtra::ggRose() 作玫瑰图df <- df %>%
group_by(Class) %>%
arrange(Survived) %>% # 确保Survived按顺序排列
mutate(ypos = 人数 - cumsum(人数) / 20) # 计算标签的垂直位置
# 定义标签角度和调色板
myangle <- seq(-20, -340, length.out = 8)
palette <- brewer.pal(n = 2, "Set3") # 根据Survived类别数选择颜色数
## Warning in brewer.pal(n = 2, "Set3"): minimal value for n is 3, returning requested palette with 3 different levels
# 绘制玫瑰图
p <- ggplot(df, aes(x = Class, y = 人数, fill = Survived)) +
geom_col(width = 1, color = "grey20", position = "stack") + # 堆叠条形图
geom_text(aes(y = ypos, label = 人数), # 添加数值标签
size = 3.5, # 标签字体大小
color = "black", # 标签颜色(与背景对比)
show.legend = FALSE) + # 不显示图例中的文本标签
coord_polar(theta = "x", start = 0) + # 极坐标转换
scale_fill_manual(values = palette) + # 手动指定填充颜色
theme(axis.text.x = element_text(size = 10, angle = myangle),
legend.position = "right") +
labs(y = "人数", title = "乘客生存情况玫瑰图")
## Warning: Vectorized input to `element_text()` is not officially supported.
## ℹ Results may be unexpected or may change in future versions of ggplot2.
print(p)
点阵图特点:
双变量交叉分析:
X轴:舱位等级(Class)
Y轴:生存状态(Survived)
点大小/颜色:映射人数,同时编码数值大小(双重视觉提示)。
视觉设计:
使用 RdYlGn
渐变调色板(红-黄-绿),红色代表高值,绿色代表低值。
点形状为实心圆(shape=21),边框与填充对比清晰。
交互潜力:
plotly
添加悬停信息(如精确数值)。传达信息:
直观对比不同舱位生存/死亡的绝对人数(如“3等舱死亡人数最多”)。
颜色和大小协同强化差异识别(如红色大点=高频组合)。
热力图特点:
矩阵式布局:
行=生存状态,列=舱位等级,单元格颜色深浅表示人数。
直接标注数值(addlabel=TRUE),避免依赖颜色判读。
颜色映射:
Reds),越深表示值越大,适合有序数据。简洁性:
传达信息:
精确展示每个交叉类别的频数(如“1等舱生存者=XX人”)。
突出极端值(如最深色单元格对应最高频组合)。
玫瑰图特点:
极坐标转换:
将柱状图转为环形布局,角度=舱位等级,半径=人数。
堆叠条形(position="stack")显示组内构成。
标签优化:
动态计算标签位置(ypos),避免重叠。
角度调整(myangle)提升可读性。
颜色对比:
Set3 分类调色板,区分生存状态。传达信息:
强调舱位对生存率的整体影响(如“3等舱扇形面积最大”)。
环形布局增强视觉冲击力,适合演示场景。
绘制Class和 Sex的饼环图。
# 按Class和Sex分组汇总人数
df <- data %>%
group_by(Class, Sex) %>%
summarise(人数 = sum(Freq), .groups = "drop") %>%
mutate(Class = factor(Class, levels = c("1st", "2nd", "3rd", "Crew")),
Sex = factor(Sex, levels = c("Male", "Female")))
datatable(df,rownames = FALSE)
ggiraphExtra::ggPieDonut()作饼环图# 绘制饼环图
ggPieDonut(data = df,
aes(pies = Class, donuts = Sex, count = 人数),
title = "(b) Class为饼图,Sex为环形图")
特点:双层嵌套设计:
外层(Pie):展示乘客舱位等级(Class)的占比分布,分为1st、2nd、3rd、Crew四个扇形。
内层(Donut):在每一舱位等级内,进一步按性别(Sex)拆分,形成环形细分(Male/Female)。
视觉编码:
扇形面积=人数比例,颜色自动分配以区分组别。
内环与外环颜色联动(如“1st”舱的Male/Female使用同色系渐变)。
标签与交互:
默认显示关键标签(如占比或数值),可通过参数调整精度。
静态图表,但支持通过plotly等工具添加悬停交互。
信息:
舱位分布:直观对比不同舱位(如3rd舱占比最大,Crew占比最小)。
性别构成:揭示同一舱位内性别比例差异(如“1st舱女性比例高于其他舱位”)。