数据挖掘与R语言

第2讲:R语言数据类型与数据结构

2026年09月03日

本讲导览

Data Types & Objects

  • 一、复习导入与新课导论 ——从"给一组数字批量涨价"说起
  • 二、R语言基本数据类型 ——数值、字符、逻辑、复数、日期时间,以及分类变量的概念
  • 三、向量(Vector) ——赋值、命名、c(),再到R语言的基本积木
  • 四、因子(Factor) ——分类变量在R里是怎样实现的
  • 五、数据框(Data Frame)初探 ——像Excel一样的表格,以及矩阵/数组/列表地图
  • 六、课堂总结与Exit Ticket ——把今天学的数据世界串成一张图

提示

今天的目标:认识单个值的数据类型,以及多个值时数据的组织结构。

一、复习导入与新课导论

从"给一组数字批量涨价"问题,引出向量

1.1 上节课复习

  • R与RStudio是什么关系?
  • 上节课我们用了哪些函数生成数列?

(提示:seq()rep()sample()——如果想不起来,说明该练习了)

1.2 情境导入 —— 如果要给一组数字都涨10%?

展示上节课练习:1到20的连续整数 1:20

"如果这20个数字分别代表20天的销售额(万元),公司决定给每天销售额都上浮10%作为下季度预测,你会怎么写代码?"

不用一个个改,R可以整体处理——这就是今天的两个关键词:向量向量化运算

1.3 今天起,主要用脚本区来写代码

  • 上节课我们一直在Console里直接敲命令、立刻看到结果——适合"试一下、看一眼"
  • 从今天开始,代码会先写在左上角的Source Editor里,并保存成脚本文件,再整段/逐行运行——适合"写一整套逻辑,反复调整、反复运行"
  • 呼应四象限口诀:"左上写,左下跑"——今天的"写"会变得更正式一点,接下来几张slide逐一讲清楚:怎么开、怎么存、怎么写得整洁、怎么运行

1.4 脚本的打开与保存

  • 新建脚本:File → New File → R Script(Ctrl+Shift+N,Mac:Cmd+Shift+N
  • 打开已有脚本:File → Open File...(Ctrl+O),或者直接在右下角Files面板里点.R文件
  • 保存Ctrl+S(Mac:Cmd+S),第一次保存会让你选文件名和位置

提示

文件名建议见名知意,比如"学号_姓名_第2课.R";建议给每门课/每个项目单独建一个文件夹,不要都堆在桌面上,方便以后查找。

注记

留意标签页上文件名前面的小圆点:有改动但还没保存时会显示一个圆点,保存后圆点消失——这是提醒你"这份文件还有没存的改动"的信号,写完记得随手Ctrl+S,避免电脑意外重启白忙一场。

1.5 写脚本的规范:注释与分段

注释#开头到这一行结束,R完全不会执行,是专门写给"人"看的

▶️ 查看代码
# 计算平均营收
revenue <- c(120, 135, 128, 150)
mean(revenue)   # 行末也可以加注释,解释这一行在做什么

提示

好的注释解释"为什么这么做",而不是简单翻译代码——比如x <- 5 # 把5赋值给x这种注释没有意义,revenue <- c(120, 135, 128, 150) # 某公司四个季度营收才是有用的注释。

分段:脚本变长之后,用RStudio的"分节"语法给代码分块,方便折叠和跳转——注释后面跟4个以上的短横线,就会自动变成一个可折叠的分节标题:

▶️ 查看代码
# 数据准备 ----
revenue <- c(120, 135, 128, 150)

# 计算指标 ----
mean(revenue)
sum(revenue)

提示

快捷键Ctrl+Shift+R(Mac:Cmd+Shift+R)可以直接插入一个分节标题;脚本变长后,按Ctrl+Shift+O(Mac:Cmd+Shift+O)打开大纲面板,点一下就能跳到对应分段,不用来回滚动鼠标找代码。

1.6 代码排版:怎么写得美观易读

基本间距习惯

▶️ 查看代码
# 不推荐:挤在一起,读起来费劲
revenue<-c(120,135,128,150)

# 推荐:赋值符号、逗号后面都留一个空格
revenue <- c(120, 135, 128, 150)
  • 运算符(<-+>等)前后加空格
  • 逗号后面加空格,逗号前面不加
  • 两者对R来说效果完全一样,纯粹是为了"人"读起来舒服——代码是写给未来的自己和同事看的,不只是写给电脑看的

什么时候该换行:一行代码太长(一般建议不超过80个字符)、或者一个函数参数比较多时,可以在逗号后换行,让每个参数单独占一行:

▶️ 查看代码
df <- data.frame(
  company = c("贵州茅台", "五粮液", "泸州老窖"),
  revenue = c(1500, 680, 320),
  rating = c("A", "A", "B")
)

这样比堆在一行里更容易检查——少个逗号、漏个括号,一眼就能看出来是哪一行的问题。

提示

拿不准怎么排版的时候,选中这段代码,按Ctrl+Shift+A(Mac:Cmd+Shift+A),RStudio会自动帮你重新排版(补空格、调整缩进),相当于"一键代码美化"。

1.7 运行代码的几种方式

想做什么 怎么操作
运行当前一行 光标停在这一行任意位置,按Ctrl+Enter(Mac:Cmd+Return),运行完自动跳到下一行
运行选中的部分代码 鼠标选中若干行(哪怕只是一行中的一部分),Ctrl+Enter只运行选中的内容
运行一整段(跨多行的语句) 光标停在这段代码任意一行即可,比如上一页跨5行的data.frame(...),R会自动识别这是"一句完整的代码",整体执行,不会只运行半句
运行整个脚本 Ctrl+Shift+Enter(Mac:Cmd+Shift+Return),或点编辑器右上角的Source按钮,从头到尾整份文件都跑一遍

提示

记口诀:一行/选中都用Ctrl+Enter,全部用Ctrl+Shift+Enter。日常写代码时最常用的是"运行当前一行"——写一行、看一眼结果、再写下一行,运行整份脚本一般用在"确认整个文件从头到尾都能顺利跑通"的时候(比如交作业前)。

1.8 今天真正要回答的问题

在R中,我们不只是"存数据",而是把数据组织成不同的数据对象——不同的对象,决定了我们以后能对这份数据做什么操作。

提示

今天这一整讲,其实都在回答一个问题:R是怎样把现实世界的数据,一步步"装进"计算机里的?

答案会是一条链条:一个值 → 向量 → 因子 / 数据框。今天先记住这条链条的样子,讲完你就会明白每一环是怎么接上的。

二、R语言的基本数据类型

数值、字符、逻辑、复数——每个数据都有自己的"身份"

2.1 数值型(numeric)

▶️ 查看代码
class(100)
[1] "numeric"
▶️ 查看代码
class(3.14)
[1] "numeric"
  • 本课程里,我们把整数和小数统一归为数值型来理解和使用
  • 更严谨地说:R内部其实区分双精度数(double)整数(integer)两种存储方式,100默认存成double;如果想强制存成真正的整数,可以用100L(结尾加大写L)
  • 这个区别在基础数据分析里几乎不影响你写代码,了解即可,不必深究
▶️ 查看代码
class(100L)     # 加L,真正的整数型
[1] "integer"

2.2 字符串型(character)

▶️ 查看代码
class("贵州茅台")
[1] "character"
▶️ 查看代码
class("A")
[1] "character"
  • 财务场景:公司名称、股票代码、评级等级等通常存为字符串型

2.3 逻辑型(logical)

▶️ 查看代码
class(TRUE)
[1] "logical"
▶️ 查看代码
5 > 3
[1] TRUE
▶️ 查看代码
100 == 100
[1] TRUE
  • 财务场景:判断某季度营收是否达标(revenue > target),结果就是逻辑型

2.4 复数型(complex,简单了解)

▶️ 查看代码
complex(real = 1, imaginary = 2)
[1] 1+2i
▶️ 查看代码
class(1+2i)
[1] "complex"
  • 财务数据分析中很少直接用到复数型,此处仅作了解,知道R语言的基本数据类型覆盖完整即可

2.5 日期与时间型(Date)

▶️ 查看代码
today <- as.Date("2026-09-03")
today
[1] "2026-09-03"
▶️ 查看代码
class(today)
[1] "Date"
▶️ 查看代码
Sys.Date()             # 系统当前日期
[1] "2026-09-03"
  • 财经场景:财报发布日、开票日期、股票交易日……这些都需要日期型,而不是普通字符串
  • 日期型不是本课程说的"四种基本类型"之一,它是R在数值型基础上专门包装出来的一个类,本质上还是靠数字存储(内部记录的是"距1970-01-01有多少天")
▶️ 查看代码
as.numeric(today)                        # 揭秘:日期在底层其实是个数字
[1] 20699
▶️ 查看代码
today - as.Date("2026-01-01")            # 日期可以直接相减,算相隔天数
Time difference of 245 days
▶️ 查看代码
format(today, "%Y年%m月%d日")             # 格式化成中文习惯的样子
[1] "2026年09月03日"

提示

知道"日期底层是数字"这件事,能帮你理解很多"奇怪"的报错——比如不小心把日期列当成普通数值做了加减,结果得到一个诡异的天数,而不是报错。

2.6 分类变量 —— 数据分析里的一个重要概念

财经数据里经常出现这类信息:所属行业(银行/科技/能源)、信用评级(低/中/高)、地区(华东/华南/华北)——它们的取值表示类别,不表示数量,统计学上把这类变量叫分类变量(categorical variable)

分类变量又分两种:

特点 例子
无序分类(nominal) 类别之间没有自然顺序 行业:银行、科技、能源
有序分类(ordinal) 类别之间自然顺序,但相邻类别的"距离"不一定相等 信用评级:低 < 中 < 高

提示

判断一个变量是不是"有序",就问一句:这些类别能不能排出先后/大小? 能排的是有序分类(如评级、学历),排不出来的是无序分类(如行业、地区)。

重要

这里先留一个悬念:R要怎么表示"这是一个分类变量"、还要区分"有没有顺序"呢? 光靠字符串是做不到的——字符串只能存文字,存不了"这几个文字是一组固定类别"这件事。我们得先学会向量,再回头看R专门为这件事设计的工具。

2.7 课堂练习

判断以下值分别属于什么类型,用class()验证:

  • "成都锦城学院"
  • TRUE
  • 2026
  • 3.14 > 3

三、向量(Vector)——R语言的基本积木

一组同类型的数据放在一起

3.1 一个悄悄话:单个数字,其实也是向量

▶️ 查看代码
100
[1] 100
▶️ 查看代码
seq(500,300, by = -3)
 [1] 500 497 494 491 488 485 482 479 476 473 470 467 464 461 458 455 452 449 446
[20] 443 440 437 434 431 428 425 422 419 416 413 410 407 404 401 398 395 392 389
[39] 386 383 380 377 374 371 368 365 362 359 356 353 350 347 344 341 338 335 332
[58] 329 326 323 320 317 314 311 308 305 302
  • 回忆一下第二部分敲的class(100),输出前面是不是总有个[1]?这不是巧合
  • 秘密:在R的世界里,没有真正意义上孤零零的"一个数字"——100本质上是一个长度为1的向量
  • 那个[1]的意思是"这一行,是从向量的第1个元素开始显示的";向量变长后换行,你会看到行首编号跳到[26]之类的位置,帮你数清楚这是第几个元素
  • 这也是为什么后面讲的索引、运算这些"向量的操作",对单个数字同样适用——因为它骨子里也是向量

3.2 赋值符号 <- —— 给数据起个名字

▶️ 查看代码
x <- 5    # 把 5 装进名字 x 里
x         # 之后就可以反复用 x 代表这个值
[1] 5
  • <- 读作"赋值":把右边的结果,装进左边这个名字里
  • 快捷键:Mac Option + -Windows Alt + -,会自动打出<-(带空格),比手打两个字符快,建议现在就养成习惯
  • = 技术上也能赋值,但本课程和R社区主流风格一样,把=留给函数参数专用(如round(x, digits = 2)),赋值统一用<-,读代码时更容易分清

3.3 变量命名规则与常见坑

硬性规则(写错R直接报错):

  • 只能包含字母、数字、._
  • 不能以数字开头2025revenue❌ → revenue_2025✅(本课件后面一直这么写)
  • 区分大小写Revenuerevenue是两个不同的变量
  • 不能是R的保留字:TRUEFALSENAifforfunction

警告

软性的坑:变量名技术上可以随便起,但起成c <- 5会把内置的c()函数"遮住",导致后面c(1,2,3)莫名报错——现场演示一下这个陷阱,起名时避开cmeansum这类常用函数名。

  • 起有意义的名字:x不如revenue一眼看懂
  • 技术上也可以用中文做变量名(现代R对中文支持已经很好),但本课程统一使用英文变量名——这是为了养成和国际教材、R扩展包、团队协作一致的编程习惯,不是因为中文变量名会出错
  • 命名风格:本课程统一用snake_case(单词间加下划线),如revenue_2025is_profit

3.4 c()函数 —— 向量的搭建工具

▶️ 查看代码
5              # 单独一个数字,长度为1
[1] 5
▶️ 查看代码
c(120, 135, 128, 150)   # 用 c() "粘"成一个向量,长度为4
[1] 120 135 128 150
  • c是英文combine(合并、组合)的缩写,作用就是把多个单独的值粘合成一个向量
  • 这是你在R里会用到最频繁的函数之一——只要看到"一组同类型的数据",第一反应就是c(...)
  • c()不仅能合并单个数值,也能合并向量本身:c(revenue, 160)就是在原向量末尾再加一个新数据

3.5 向量的创建

▶️ 查看代码
quarter <- c("Q1", "Q2", "Q3", "Q4")     # 四个季度标签
revenue <- c(120, 135, 128, 150)         # 某公司四个季度营收(单位:万元)
is_profit <- c(TRUE, TRUE, FALSE, TRUE)
revenue
[1] 120 135 128 150

警告

向量中所有元素必须是同一种数据类型,否则R会自动"降级"转换——c(1, "a") 会把 1 也变成字符串 "1"。现场试一下这个"陷阱"。

课堂练习:创建一个包含你所在小组5名同学姓名的字符向量

3.6 向量的索引 —— 怎么取出想要的那个数

R的索引本质上只回答一个问题:我想要哪些位置?

▶️ 查看代码
revenue[1]               # 第1个位置
[1] 120
▶️ 查看代码
revenue[2:3]             # 第2、3个位置
[1] 135 128
▶️ 查看代码
revenue[-1]              # 除第1个位置外的所有位置(负索引=排除)
[1] 135 128 150
▶️ 查看代码
revenue[c(1, 3)]         # 第1、3个位置
[1] 120 128

正向、负向、逻辑索引看起来是三种语法,其实都在做同一件事——x[ ]就是从x中选出我想要的元素,这个统一认知对后面筛选数据框非常重要。

逻辑索引拆开看一步

▶️ 查看代码
revenue > 130             # 先问每个位置"要不要",得到TRUE/FALSE
[1] FALSE  TRUE FALSE  TRUE
▶️ 查看代码
revenue[revenue > 130]    # R把TRUE对应的位置留下来
[1] 135 150
  • 财务场景练习:从revenue中找出所有营收超过平均水平的季度

重要

跟 Python 不一样! Python里revenue[-1]是"取最后一个",但R里的负索引是"排除"——revenue[-1]意思是"除了第一个之外的所有元素",不是"最后一个"。要真正取到最后一个值,得用下面这两种写法:

▶️ 查看代码
revenue[length(revenue)]   # 先用length()算出向量长度,再用这个位置去取
[1] 150
▶️ 查看代码
tail(revenue, 1)           # tail()取"尾部"n个元素,n=1就是最后一个
[1] 150

课堂练习:写出获取revenue中最后一个季度数据的两种不同写法

3.7 向量化运算 —— R比你想象的更聪明

▶️ 查看代码
revenue * 1.1                 # 所有季度营收上浮10%
[1] 132 148 141 165
▶️ 查看代码
revenue - mean(revenue)       # 每个季度与平均值的差异
[1] -13.25   1.75  -5.25  16.75
▶️ 查看代码
sum(revenue)                  # 全年总营收
[1] 533
▶️ 查看代码
mean(revenue)                 # 平均季度营收
[1] 133
▶️ 查看代码
max(revenue) - min(revenue)   # 季度营收波动幅度
[1] 30

对比一下:如果不用向量化,得这样写

▶️ 查看代码
for (i in 1:length(revenue)) {
  print(revenue[i] * 1.1)
}
[1] 132
[1] 148
[1] 141
[1] 165

哪一种更符合今天"批量处理一组数据"的任务?答案很直观。

重要

在R中,如果一个操作可以自然地向量化完成,优先考虑向量化,而不是手动写循环——这是R处理数据的核心优势,不代表循环是坏东西,只是很多场景下向量化更简洁、更不容易出错。回到开头的问题:现在能一行代码算出20天销售额上浮10%后的结果了吗?(1:20) * 1.1

课堂练习:某产品连续6个月销售额为c(45,52,48,60,55,58),计算总销售额、平均销售额,并找出销售额超过50的月份

3.8 常用向量函数 —— 锦上添花的小工具

▶️ 查看代码
length(revenue)                     # 向量长度(有几个季度)
[1] 4
▶️ 查看代码
sort(revenue)                       # 从小到大排序
[1] 120 128 135 150
▶️ 查看代码
sort(revenue, decreasing = TRUE)    # 从大到小排序
[1] 150 135 128 120
▶️ 查看代码
which.max(revenue)                  # 营收最高的是第几季度
[1] 4
▶️ 查看代码
which.min(revenue)                  # 营收最低的是第几季度
[1] 1
▶️ 查看代码
quarter[which.max(revenue)]         # which.max()告诉你"第几个",再用这个位置去问quarter"是谁"
[1] "Q4"
  • 财经场景:which.max()找到位置,quarter[...]结合这个位置反查"是哪个季度",这个"先定位、再反查"的思路,为项目二"数据准备"中按条件筛选数据打下基础
  • 课堂练习:找出revenue中第二高的季度营收是多少(提示:先sort()再取值)

四、因子(Factor)——分类变量在R中的实现

回收一个悬念:R怎么表示"分类"这件事?

4.1 什么是因子

还记得第二部分留下的悬念吗?——分类变量要怎么在R里表示?现在你已经学会向量了,答案揭晓:

▶️ 查看代码
rating <- c("A", "B", "A", "C", "B")   # 先看字符向量的写法
class(rating)
[1] "character"

字符向量能存下这几个字母,但它不知道"A、B、C是一组固定的类别"——它只当这是普通文本。R专门设计了因子(factor)来解决这个问题:它不仅记录每条数据属于哪个类别,还记录这个变量总共有哪些可能的类别(levels)。

注记

因子到底算类型还是算结构? 老实说,两边都不完全是——它在R底层是"整数向量 + 一张标签表",所以天生卡在中间:从使用体验上看,它更像字符型的一个"专业版"(表示分类文本);从底层实现看,它建立在向量之上。这一讲刚学的日期型其实也是同样的处理方式(数值向量+特殊标记)。记住它是"分类变量在R里的具体实现"就够了,不用纠结该归到哪一类。

4.2 因子的创建与查看 —— 先看无序分类

▶️ 查看代码
rating_f <- factor(rating, levels = c("A", "B", "C"))
class(rating_f)
[1] "factor"
▶️ 查看代码
levels(rating_f)      # 查看有哪些类别
[1] "A" "B" "C"
▶️ 查看代码
table(rating_f)       # 统计各评级公司数量
rating_f
A B C 
2 2 1 

注记

因子的"水平"(levels)就是它可能取值的全部类别,这是因子与普通字符串最大的区别。这里的rating无序分类——A、B、C之间不存在谁比谁"更高"的关系,只是三个不同标签。

4.3 有序因子 —— 当类别有高低之分时

▶️ 查看代码
risk <- factor(c("低", "中", "高", "中", "低"),
                levels = c("低", "中", "高"), ordered = TRUE)
risk                # 打印时会显示 低 < 中 < 高 的顺序
[1] 低 中 高 中 低
Levels: 低 < 中 < 高
▶️ 查看代码
risk[1] < risk[3]    # TRUE,因为"低" < "高"
[1] TRUE

这里的risk有序分类——多了ordered = TRUE和按顺序排好的levels,R就知道"低<中<高"这个大小关系,能直接比较。财务场景:风险等级、信用评级都天然带有高低顺序,用有序因子表示比普通字符串更符合业务逻辑,为后续回归分析中"虚拟变量"的处理打下基础。

课堂练习:将某公司四个季度的"业绩评价"(合格、优秀、良好、优秀)转换为因子并用table()统计各等级出现次数

五、数据框(Data Frame)初探

像Excel一样的表格

5.1 数据框是什么

类比:Excel中一行是一条记录,一列是一个字段;数据框也是如此,只不过每一"列"背后其实就是我们刚学的向量

5.2 数据框的创建

▶️ 查看代码
company <- c("贵州茅台", "五粮液", "泸州老窖")
revenue_2025 <- c(1500, 680, 320)    # 单位:亿元
rating_f <- factor(c("A", "A", "B"), levels = c("A", "B", "C"))
df <- data.frame(company, revenue_2025, rating_f)
df
   company revenue_2025 rating_f
1 贵州茅台         1500        A
2   五粮液          680        A
3 泸州老窖          320        B

5.3 数据框的基本查看与列访问

▶️ 查看代码
str(df)                          # 查看数据框结构(每列的类型)
'data.frame':   3 obs. of  3 variables:
 $ company     : chr  "贵州茅台" "五粮液" "泸州老窖"
 $ revenue_2025: num  1500 680 320
 $ rating_f    : Factor w/ 3 levels "A","B","C": 1 1 2
▶️ 查看代码
dim(df)                          # 几行几列
[1] 3 3
▶️ 查看代码
names(df)                        # 列名
[1] "company"      "revenue_2025" "rating_f"    
▶️ 查看代码
df$revenue_2025                  # 取出"营收"这一列(本质还是一个向量!)
[1] 1500  680  320

注记

数据框的索引统一写成 df[行, 列]——逗号左边选行,右边选列,不写就代表"全部"。所以:

▶️ 查看代码
df[df$revenue_2025 > 500, ]              # 行:营收>500;列:不写=全部列
   company revenue_2025 rating_f
1 贵州茅台         1500        A
2   五粮液          680        A
▶️ 查看代码
df[df$revenue_2025 > 500, "company"]     # 行:营收>500;列:只要company
[1] "贵州茅台" "五粮液"  

注记

数据框的每一"列"本质就是一个向量——这也是为什么前面要先扎实掌握向量操作。数据框只是把多个向量按行对齐组合在一起。完整的数据导入(CSV/Excel)、数据清洗与变换操作,将在项目二"数据准备"中系统展开,今天只做初步认识。

课堂互动:数据框和Excel表格有什么相似之处?又有什么是Excel做不到、但R数据框能做到的?

5.4 认识R自带的数据集 —— 不用总是自己造数据

R和很多扩展包里自带了大量现成的数据框,可以直接拿来用,不用每次都自己敲c()

▶️ 查看代码
class(LifeCycleSavings)     # 这是R自带的一个真实经济数据集
[1] "data.frame"
▶️ 查看代码
head(LifeCycleSavings, 5)   # 查看前5行:各国储蓄率与人口、收入相关指标
             sr pop15 pop75  dpi ddpi
Australia 11.43  29.4  2.87 2330 2.87
Austria   12.07  23.3  4.41 1508 3.93
Belgium   13.17  23.8  4.43 2108 3.82
Bolivia    5.75  41.9  1.67  189 0.22
Brazil    12.88  42.2  0.83  728 4.56
▶️ 查看代码
str(LifeCycleSavings)       # 每一列分别是什么类型
'data.frame':   50 obs. of  5 variables:
 $ sr   : num  11.43 12.07 13.17 5.75 12.88 ...
 $ pop15: num  29.4 23.3 23.8 41.9 42.2 ...
 $ pop75: num  2.87 4.41 4.43 1.67 0.83 2.85 1.34 0.67 1.06 1.14 ...
 $ dpi  : num  2330 1508 2108 189 728 ...
 $ ddpi : num  2.87 3.93 3.82 0.22 4.56 2.43 2.67 6.51 3.08 2.8 ...
  • LifeCycleSavings是R自带的经济学数据集,每一行是一个国家,列包括总储蓄率(sr)、少儿/老年人口占比(pop15/pop75)、人均可支配收入(dpi)及其增长率(ddpi
  • data()可以列出当前已加载扩展包里所有自带数据集的名字,感兴趣可以自己找几个看看
▶️ 查看代码
LifeCycleSavings[LifeCycleSavings$dpi > 2000, c("dpi", "sr")]   # 综合运用:行筛选+列选取
               dpi    sr
Australia     2330 11.43
Belgium       2108 13.17
Canada        2983  8.79
Denmark       2497 16.85
France        2214 12.64
Germany       2457 12.55
Luxembourg    2449 10.35
Norway        2231 10.25
Sweden        3299  6.86
Switzerland   2631 14.13
United States 4002  7.56

5.5 拓展地图 —— R还有哪些数据结构

今天重点掌握的是向量数据框,但R还有三个"近亲"结构,值得知道它们的存在和大致定位(不要求今天就会用):

矩阵:matrix

▶️ 查看代码
matrix(1:6, nrow = 2)                    # 矩阵:二维、且所有元素必须同一类型
     [,1] [,2] [,3]
[1,]    1    3    5
[2,]    2    4    6

数组:array

, , 1

     [,1] [,2] [,3]
[1,]    1    3    5
[2,]    2    4    6

, , 2

     [,1] [,2] [,3]
[1,]    7    9   11
[2,]    8   10   12

, , 3

     [,1] [,2] [,3]
[1,]   13   15   17
[2,]   14   16   18

, , 4

     [,1] [,2] [,3]
[1,]   19   21   23
[2,]   20   22   24

列表:list

$name
[1] "贵州茅台"

$price
[1] 1680

$code
[1] "600519"
结构 维度 元素类型 一句话定位
向量 Vector 一维 必须同类型 今天的主角,最基本的积木
矩阵 Matrix 二维 必须同类型 向量的二维版本
数组 Array 可以更多维 必须同类型 矩阵的高维版本
列表 List 不限 可以不同类型 最灵活的"百宝箱"
数据框 Data Frame 二维(行×列) 列与列之间可以不同类型 分析数据最常用的结构

提示

一个值得记住的关系:数据框本质上是一种特殊的列表——每一列是列表里的一个元素(一个向量),只是要求所有列长度相等、摆成表格的样子。以后你会在str(df)的输出里看到List of ...字样,就是这个原因。

矩阵/数组主要用在纯数值计算(比如矩阵乘法),列表常用来打包"一次分析的所有结果"(比如既要存数字又要存图表)。这两个今天不展开操作,项目后续用到时再详细讲。

六、课堂总结与Exit Ticket

把今天学的数据世界串成一张图

6.1 本讲知识回顾

flowchart TD
    R["R中的数据"] --> V0["一个值<br/>其实是长度为1的向量"]
    R --> V["多个值<br/>向量 Vector"]
    V --> T["元素的数据类型<br/>数值/字符/逻辑/复数/日期"]
    V --> F["因子 Factor<br/>分类变量的R实现"]
    V --> M["矩阵/数组<br/>向量的二维/高维版本"]
    V --> L["列表 List<br/>可装不同类型的百宝箱"]
    L --> D["数据框 Data Frame<br/>一种特殊的列表"]

    style R fill:#1a3a5c,color:#fff
    style V0 fill:#2e5984,color:#fff
    style V fill:#2e5984,color:#fff
    style T fill:#375623,color:#fff
    style F fill:#375623,color:#fff
    style M fill:#375623,color:#fff
    style L fill:#375623,color:#fff
    style D fill:#843c0c,color:#fff

  • 数据类型(含分类变量概念) → 向量(创建、索引、运算) → 因子(分类变量的R实现) → 矩阵/数组/列表(地图了解) → 数据框(一种特殊的列表)
  • 核心逻辑:"数据框是向量的组合,因子是分类变量在R里的实现"——这条主线贯穿今天所有内容
  • 更好记的一句话:值 → 向量 → 数据框(其实值本身就是长度为1的向量);因子是"分类变量+向量",数据框是"多个等长向量拼成的特殊列表"
  • 向量化运算是R语言的核心优势:能自然向量化的操作,优先向量化,而不是手动写循环

6.2 学习成果自查

对照一下,今天这几件事你都做到了吗?

  • ✓ 能说出R语言的基本数据类型,包括日期时间型
  • ✓ 知道单个数字其实也是"长度为1的向量"
  • ✓ 能区分无序分类变量和有序分类变量
  • ✓ 能够创建向量并完成正向、负向、逻辑索引
  • ✓ 能够运用向量化运算完成批量计算
  • ✓ 能够创建因子(含有序因子)并用table()统计类别
  • ✓ 能够创建简单数据框并用$[行,列]提取指定内容
  • ✓ 知道矩阵、数组、列表大致是什么、和向量/数据框是什么关系
  • ✓ 会用head()/str()查看一个R自带的数据集

提示

如果有没打勾的,下课后一定要找同学或老师补上,不要留到下一讲。

6.3 Exit Ticket —— 写给自己的三个问题

请花1分钟,在纸条或在线问卷上简要回答:

  1. 因子和普通字符向量有什么区别?信用评级适合用无序因子还是有序因子?
  2. 如果revenue <- c(80, 120, 90, 150),怎么选出所有超过100的值?
  3. 数据框和列表是什么关系?
  4. 今天最有挑战的一个操作是什么?(选做,帮老师收集反馈)

注记

这不是考试,是帮你自己梳理今天学到了什么,也帮老师了解下节课该怎么调整节奏。

课后作业

向量与数据类型练习

在RStudio中新建一个R脚本(.R文件),完成以下操作并保留代码与结果:

  1. 判断以下数据的类型:100"财务分析"TRUE3.14
  2. 创建一个包含某公司近6个月销售额的向量(数据自定),完成:
    • 计算总销售额与平均销售额
    • 找出销售额最高和最低的月份(用which.max()/which.min()
    • 计算每月销售额相对于平均值的偏差(向量减法)

课后作业(续)

因子与数据框练习

  1. 创建一个因子,表示某班5名同学的考试等级(优/良/中/差),并用table()统计各等级人数
  2. 创建一个数据框,至少包含3列(如"姓名""分数""等级"),并完成:
    • str()查看结构
    • $取出"分数"这一列
    • 筛选出分数大于等于90的记录

注记

财务综合小练习:某公司三个产品(A、B、C)某月销售额分别为85万元、120万元、96万元,请用向量表示这组数据,计算总销售额、平均销售额,并找出表现最好的产品

提交要求

将上述练习的代码和运行结果截屏,整理在一个Word文档中,命名为"学号_姓名_第2课作业.docx"提交。本次作业计入平时成绩中的"实验报告"部分,请按时提交并保证代码可运行、截图清晰。

这是我们最后一次要求"截图+整理Word"的作业形式。 从第3讲开始,我们会用Quarto一键把代码和结果直接生成报告——你现在手动做的这件事,很快就会变成计算机自动帮你完成。

下讲预告

第3讲:Markdown语法与Quarto文档写作

  • 从"截图整理报告"到"一键Render生成报告"
  • Markdown基础语法 + Quarto文档结构(YAML、代码块、行内代码)
  • 从第3讲开始,主要用Quarto文档演示——今天学的向量、因子、数据框代码,很快就会变成报告里的示例

提示

课前准备:确保R脚本能正常保存、运行;如果RStudio还有装不上的问题,提前联系老师。

谢谢!

第2讲:R语言数据类型与数据结构

"In God we trust; all others must bring data." — W. Edwards Deming,质量管理与统计学家

朱 奇 | 锦城大学 · 财会学院