用 R 与 ggplot2 可视化数量:Data Science for Beginners 鸟类数据集折线图、散点图与柱状图实战
发布时间:2026/9/10 9:56:06 作者:尧图编辑部 阅读量:1,286

用 R 与 ggplot2 可视化数量Data Science for Beginners 鸟类数据集折线图、散点图与柱状图实战【免费下载链接】Data-Science-For-Beginners10 Weeks, 20 Lessons, Data Science for All!项目地址: https://gitcode.com/GitHub_Trending/da/Data-Science-For-Beginners本文以微软开源课程 Data Science for Beginners 中第 9 课《Visualizing Quantities》的 R 语言实现为骨架带你使用ggplot2基于明尼苏达州鸟类数据集data/birds.csv完成从折线图、散点图到柱状图的完整可视化流程。读完本文你将掌握图形语法Grammar of Graphics的核心思想、ggplot()的声明式绘图套路、异常值识别与数据过滤、以及用dplyr分组聚合后绘制可读性更高的统计图表。本课对应的原始英文讲义位于 3-Data-Visualization/R/09-visualization-quantities/README.md仓库中同时提供 Python 版本3-Data-Visualization/09-visualization-quantities/README.md便于两种语言对照学习。ggplot2 与图形语法一次声明式的绘图体验ggplot2是 R 生态中最受欢迎的绘图包之一既能生成简单图表也能胜任复杂的高级图形。它的底层设计理念是图形语法The Grammar of Graphics——一种将图形拆解为语义组件的通用可视化方案例如尺度scales与图层layers。换句话说你只需要用少量代码就能完成单变量或多变量数据的可视化告诉ggplot2如何把变量映射到美学属性aesthetics、使用哪种图形原语geometry剩下的事情由它包办。✅绘图公式Plot Data Aesthetics GeometryData指的是数据集本身Aesthetics指明要研究的变量即 x 与 y 变量Geometry指明图表的几何类型折线图、柱状图等一般性的绘图流程包括四步先定位数据框中想要呈现的列再对数据执行必要的转换随后把变量赋给 x 轴与 y 轴最后选定图表类型并渲染输出。ggplot()的管道式写法号逐层叠加让每一步都清晰可见。选择哪种几何类型图表取决于你的数据和你想讲述的故事分析目的推荐图表类型分析趋势trends折线图、柱状图比较数值compare values柱状图、饼图、散点图展示部分与整体的关系parts to a whole饼图展示数据分布distribution散点图、柱状图展示数值间的关系relationships折线图、散点图、气泡图准备数据读取明尼苏达鸟类数据集打开 R 控制台导入数据集。注意该数据集存放在本仓库根目录下的 data/birds.csv共 442 条鸟类记录、13 个字段文件带 UTF-8 BOM 头因此读取时必须显式指定fileEncodingUTF-8-BOM否则列名可能出现乱码birds - read.csv(data/birds.csv, fileEncoding UTF-8-BOM) head(birds)head()返回数据的前 5 行内容是文本与数字的混合体各列含义如下列名含义Name / ScientificName常用名 / 学名Category类别如 Ducks/Geese/WaterfowlOrder / Family / Genus林奈分类学中的目 / 科 / 属ConservationStatus保护状态IUCN 等级缩写LC 无危、NT 近危、VU 易危、EN 濒危、CR 极危、EX 灭绝MinLength / MaxLength最小 / 最大体长厘米MinBodyMass / MaxBodyMass最小 / 最大体重克MinWingspan / MaxWingspan最小 / 最大翼展厘米前五行示例NameScientificNameCategoryOrderFamilyGenusConservationStatusMinLengthMaxLengthMinBodyMassMaxBodyMassMinWingspanMaxWingspan0Black-bellied whistling-duckDendrocygna autumnalisDucks/Geese/WaterfowlAnseriformesAnatidaeDendrocygnaLC4756652102076941Fulvous whistling-duckDendrocygna bicolorDucks/Geese/WaterfowlAnseriformesAnatidaeDendrocygnaLC4553712105085932Snow gooseAnser caerulescensDucks/Geese/WaterfowlAnseriformesAnatidaeAnserLC6479205040501351653Rosss gooseAnser rossiiDucks/Geese/WaterfowlAnseriformesAnatidaeAnserLC57.364106615671131164Greater white-fronted gooseAnser albifronsDucks/Geese/WaterfowlAnseriformesAnatidaeAnserLC648119303310130165折线图观察最大翼展并发现异常值先绘制基础折线图看看这些鸟类的最大翼展MaxWingspan是什么分布install.packages(ggplot2) library(ggplot2) ggplot(data birds, aes(x Name, y MaxWingspan, group 1)) geom_line()这里先安装ggplot2包再用library(ggplot2)将其载入工作区。绘图时调用ggplot()函数以data指定数据集、在aes()中指定 x、y 变量由于目标是折线图几何层选用geom_line()。注意group 1的作用当 x 轴是离散的分类变量鸟名时它告诉 ggplot 把所有点连成一条折线而不是按分组断开。第一眼你能发现什么图中至少存在一个异常值——那条翼展竟然超过 2000 厘米也就是 20 多米难道明尼苏达上空有翼龙在盘旋吗显然需要调查一下。虽然你可以在 Excel 里快速排序找出这些异常值它们多半是录入时的笔误但本课更推荐在绘图过程中解决问题也就是继续用可视化手段定位它们。给 x 轴加上标签指明涉及的鸟类种类ggplot(data birds, aes(x Name, y MaxWingspan, group 1)) geom_line() theme(axis.text.x element_text(angle 45, hjust 1)) xlab(Birds) ylab(Wingspan (CM)) ggtitle(Max Wingspan in Centimeters)这里通过theme()中的axis.text.x element_text(angle 45, hjust 1)将 x 轴刻度文本旋转 45 度、并向右对齐hjust 1避免过长的鸟名互相重叠xlab()与ylab()分别设置 x、y 轴标签ggtitle()为图表命名。即使把标签旋转到 45 度鸟名依然太多、难以阅读。换一种策略只标注异常值并把标注放进图内。此时改用散点图为标注腾出更多空间ggplot(data birds, aes(x Name, y MaxWingspan, group 1)) geom_point() geom_text(aes(label ifelse(MaxWingspan 500, as.character(Name), )), hjust 0, vjust 0) theme(axis.title.x element_blank(), axis.text.x element_blank(), axis.ticks.x element_blank()) ylab(Wingspan (CM)) ggtitle(Max Wingspan in Centimeters)这段代码做了什么geom_point()绘制散点geom_text()配合ifelse(MaxWingspan 500, as.character(Name), )只对翼展超过 500 厘米的鸟显示名称标签其余留空theme()中隐藏了 x 轴的标题、刻度文本与刻度线element_blank()让画面更清爽。⚠️排错提示原讲义中theme(...)一行末尾漏写了管道连接符直接以换行接ylab(...)会导致语法错误。实际运行时请务必像上文那样让每一层都以结束最后一行除外。过滤数据剔除异常值从散点图可以看出秃鹰Bald Eagle和草原隼Prairie Falcon虽然确实是大型猛禽但它们的最大翼展多半被录错了——多打了一个 0。你不太可能遇见翼展 25 米的秃鹰。让我们新建一个不包含这两个异常值的数据框birds_filtered - subset(birds, MaxWingspan 500) ggplot(data birds_filtered, aes(x Name, y MaxWingspan, group 1)) geom_point() ylab(Wingspan (CM)) xlab(Birds) ggtitle(Max Wingspan in Centimeters) geom_text(aes(label ifelse(MaxWingspan 500, as.character(Name), )), hjust 0, vjust 0) theme(axis.text.x element_blank(), axis.ticks.x element_blank())subset(birds, MaxWingspan 500)生成新数据框birds_filtered随后在其上绘制散点图。过滤掉异常值后数据变得更紧凑、更易理解。细节说明经过MaxWingspan 500过滤后geom_text()里的ifelse(MaxWingspan 500, ...)条件已不可能为真因此标注层实际上不会输出任何文本——它只是沿用了上一步的代码。若想保留标注应把阈值降到 500 以下这也提醒我们清理数据后要同步复核下游的过滤逻辑。现在至少在翼展维度上我们拥有了一份更干净的数据集。折线图与散点图可以展示数值及其分布但接下来我们更关心数据集中数量层面的内在信息。可以围绕下面这些量化问题创建可视化数据集里有多少种鸟类类别各类别数量是多少有多少鸟处于灭绝、濒危、稀有或常见状态按林奈分类学统计不同属Genus和目Order各有多少种鸟柱状图探索类别分布柱状图非常适合展示数据的分组聚合结果。先探索数据集中的鸟类类别看看哪一类数量最多。install.packages(dplyr) install.packages(tidyverse) library(lubridate) library(scales) library(dplyr) library(ggplot2) library(tidyverse) birds_filtered %% group_by(Category) %% summarise(n n(), MinLength mean(MinLength), MaxLength mean(MaxLength), MinBodyMass mean(MinBodyMass), MaxBodyMass mean(MaxBodyMass), MinWingspan mean(MinWingspan), MaxWingspan mean(MaxWingspan)) %% gather(key, value, -c(Category, n)) %% ggplot(aes(x Category, y value, group key, fill key)) geom_bar(stat identity) scale_fill_manual(values c(#D62728, #FF7F0E, #8C564B, #2CA02C, #1F77B4, #9467BD)) xlab(Category) ggtitle(Birds of Minnesota)这段代码用到了dplyr与lubridate两个辅助包tidyverse一并载入以便使用%%管道和gather()首先按鸟类Category分组再用summarise()对MinLength、MaxLength、MinBodyMass、MaxBodyMass、MinWingspan、MaxWingspan六列求均值并统计每组数量n n()随后gather()把六列指标长表化为key/value两列最后交给ggplot()绘制分组柱状图。scale_fill_manual()为不同指标指定了六种颜色#D62728、#FF7F0E、#8C564B、#2CA02C、#1F77B4、#9467BDstat identity表示直接使用 y 值本身作为柱高而非计数。不过这张柱状图几乎不可读——未经充分聚合的指标太多、柱子过密。应该只选择真正想展示的指标。既然类别数量众多可以改用纵向横向条形展示并调整高度以容纳全部数据birds_count - dplyr::count(birds_filtered, Category, sort TRUE) birds_count$Category - factor(birds_count$Category, levels birds_count$Category) ggplot(birds_count, aes(Category, n)) geom_bar(stat identity) coord_flip()思路如下dplyr::count(birds_filtered, Category, sort TRUE)统计Category列每个类别的出现次数并按数量降序排序存入新数据框birds_countfactor(birds_count$Category, levels birds_count$Category)把类别列转成**因子factor**并锁定其顺序确保柱状图按排序后的顺序绘制geom_bar(stat identity)用计数n作柱高coord_flip()把坐标系翻转 90 度柱子横向排列长类别名就能完整显示。这张图清楚地展示了每个类别的鸟类数量一眼就能看出数量最多的是Ducks/Geese/Waterfowl鸭/鹅/水禽类别。明尼苏达是万湖之州land of 10,000 lakes这个结果并不意外。对 data/birds.csv 的实际统计也印证了这一点Ducks/Geese/Waterfowl 共 45 条记录位列第一其次是 New World warblers41 条与 Sandpipers/Allies34 条。如果按保护状态统计LC无危占绝大多数402 条NT近危27 条、VU易危10 条、EN濒危2 条、CR极危1 条、EX灭绝1 条。✅ 不妨再对这份数据集尝试其他计数维度看看是否有让你惊讶的发现。比较数据按类别聚合与叠加柱状图通过创建新的分组轴可以对聚合数据做各种比较。比如按鸟类类别比较其最大体长MaxLengthbirds_grouped - birds_filtered %% group_by(Category) %% summarise( MaxLength max(MaxLength, na.rm T), MinLength max(MinLength, na.rm T) ) %% arrange(Category) ggplot(birds_grouped, aes(Category, MaxLength)) geom_bar(stat identity) coord_flip()先用group_by(Category)对birds_filtered分组summarise()用max()求出每类的最大体长na.rm T忽略缺失值注意讲义此处MinLength也取了 max属笔误可依需求改为min()arrange(Category)按类别排序最后绘制横向柱状图。结果毫无悬念蜂鸟hummingbirds的最大体长比鹈鹕Pelicans或鹅Geese小得多。当数据符合常识时说明分析是靠谱的还可以通过**叠加superimpose**数据做出更有信息量的柱状图。下面把每个鸟类类别的最小体长与最大体长叠加在同一张图上ggplot(data birds_grouped, aes(x Category)) geom_bar(aes(y MaxLength), stat identity, position identity, fill blue) geom_bar(aes(y MinLength), stat identity, position identity, fill orange) coord_flip()两个geom_bar()分别以MaxLength和MinLength为柱高position identity让两组柱子从同一基线0出发、互不位移地重叠绘制蓝色表示最大体长、橙色表示最小体长最后coord_flip()转为横向布局。叠加之后每个类别的体长区间一目了然蓝橙两条柱的起点相同、长度不同直观呈现了每个类别内部的体长跨度。实战挑战把方法迁移到新数据集这份鸟类数据集蕴含了特定生态系统内不同鸟类的丰富信息。不妨上网寻找其他面向鸟类的数据集例如不同州、不同国家的鸟类观测数据用同样的三件套——折线图、散点图、柱状图——围绕这些数据反复练习去发现一些你以前不知道的事实。课后巩固与作业本课是使用ggplot2可视化数量的第一课。除了ggplot2R 生态中还有 Lattice 与 Plotly 等可视化包可以继续研究如何用它们处理同一类数据集。配套作业《Lines, Scatters, and Bars》位于 translations/ar/3-Data-Visualization/R/09-visualization-quantities/assignment.md英文版见 3-Data-Visualization/R/09-visualization-quantities/assignment.md在本次课学习过的折线图、散点图和柱状图基础上深入挖掘数据集围绕某一种鸟类例如雪雁 Snow Goose编写一个脚本用三种图表讲一个完整的数据故事。评分标准包括脚本是否带有良好的注释、叙事是否完整、图表是否美观。仓库中的佐证资料一览数据集data/birds.csv含 BOM 头442 条记录、13 列故读取需fileEncodingUTF-8-BOM本课英文原始讲义3-Data-Visualization/R/09-visualization-quantities/README.md本课作业translations/ar/3-Data-Visualization/R/09-visualization-quantities/assignment.mdPython 对照版本3-Data-Visualization/09-visualization-quantities/README.md课程框架总览1-Introduction/README.md。以上所有 R 代码均在 R 控制台可直接运行绘图前的核心数据转换分组、聚合、过滤由dplyr完成绘图本身完全由ggplot2的图层叠加机制驱动这正是图形语法声明式绘图的精髓——你只管描述数据是什么、映射到哪里、用什么几何呈现剩下的交给ggplot2。【免费下载链接】Data-Science-For-Beginners10 Weeks, 20 Lessons, Data Science for All!项目地址: https://gitcode.com/GitHub_Trending/da/Data-Science-For-Beginners创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考