数据操作
quarto install tinytex
选择列修改列
复杂的数据操作可以分解为5种基本数据操作的组合:
select() — 选择列
filter()/slice() — 筛选行
arrange() — 对行排序
mutate() — 修改列/创建新列
summarize() — 汇总
都可以与
- group_by() — 分组
连用,以改变数据操作的作用域
一、选择列
- 选择列,包括对数据框做选择列、调整列序、重命名列
# A tibble: 6 × 8
class name sex chinese math english moral science
<chr> <chr> <chr> <dbl> <dbl> <dbl> <dbl> <dbl>
1 六1班 何娜 女 87 92 79 9 10
2 六1班 黄才菊 女 95 77 75 NA 9
3 六1班 陈芳妹 女 79 87 66 9 10
4 六1班 陈学勤 男 NA 79 66 9 10
5 六1班 陈祝贞 女 76 79 67 8 10
6 六1班 何小薇 女 83 73 65 8 9
1.选择列语法
(1)用列名或索引选择列
(2)借助运算符选择列
用 : 学者连续的若干列
用 !选择变量集合的余集(反选)
用 &和|选择变量集合的交或并
用 c() 合并多个选择
(3)借助选择助手函数
everything():选择所有列
last_col():选择最后一列或倒数第几列
选择列名匹配的列
start_with():以某前缀开头的列名
end_with():以某后缀结尾的列名
contains():包含某字符串的列名
matches():匹配正则表达式的列名
num_range():匹配数值范围的列名:如num_range(“x”, 1:3) 匹配x1, x2, x3
结合函数选择列:where(),比如where与is.numeric()连用选择数值列
2.一些选择的示例
# A tibble: 50 × 2
math moral
<dbl> <dbl>
1 92 9
2 77 NA
3 87 9
4 79 9
5 79 8
6 73 8
7 80 8
8 80 9
9 NA 8
10 55 8
# … with 40 more rows
根据条件(逻辑判断)选择列,选择所有数值型的列
# A tibble: 50 × 5
chinese math english moral science
<dbl> <dbl> <dbl> <dbl> <dbl>
1 87 92 79 9 10
2 95 77 75 NA 9
3 79 87 66 9 10
4 NA 79 66 9 10
5 76 79 67 8 10
6 83 73 65 8 9
7 NA 80 68 8 9
8 57 80 60 9 9
9 77 NA 54 8 10
10 68 55 66 8 9
# … with 40 more rows
自定义返回TRUE或FALSE的判断函数,支持purr风格公式
# A tibble: 50 × 2
chinese math
<dbl> <dbl>
1 87 92
2 95 77
3 79 87
4 NA 79
5 76 79
6 83 73
7 NA 80
8 57 80
9 77 NA
10 68 55
# … with 40 more rows
选择唯一值数目小于10的列(去重后数目小于10)
3.用”-“输出列
# A tibble: 50 × 5
class sex math english moral
<chr> <chr> <dbl> <dbl> <dbl>
1 六1班 女 92 79 9
2 六1班 女 77 75 NA
3 六1班 女 87 66 9
4 六1班 男 79 66 9
5 六1班 女 79 67 8
6 六1班 女 73 65 8
7 六1班 男 80 68 8
8 六1班 男 80 60 9
9 六1班 女 NA 54 8
10 六1班 女 55 66 8
# … with 40 more rows
4.调整列的顺序
列是根据被选择的顺序排列:
# A tibble: 50 × 6
name chinese science math class sex
<chr> <dbl> <dbl> <dbl> <chr> <chr>
1 何娜 87 10 92 六1班 女
2 黄才菊 95 9 77 六1班 女
3 陈芳妹 79 10 87 六1班 女
4 陈学勤 NA 10 79 六1班 男
5 陈祝贞 76 10 79 六1班 女
6 何小薇 83 9 73 六1班 女
7 雷旺 NA 9 80 六1班 男
8 陈欣越 57 9 80 六1班 男
9 黄亦婷 77 10 NA 六1班 女
10 陈媚 68 9 55 六1班 女
# … with 40 more rows
everyting()返回未被选择的所有列,将某一列移动到第一列时很方便
# A tibble: 50 × 8
math class name sex chinese english moral science
<dbl> <chr> <chr> <chr> <dbl> <dbl> <dbl> <dbl>
1 92 六1班 何娜 女 87 79 9 10
2 77 六1班 黄才菊 女 95 75 NA 9
3 87 六1班 陈芳妹 女 79 66 9 10
4 79 六1班 陈学勤 男 NA 66 9 10
5 79 六1班 陈祝贞 女 76 67 8 10
6 73 六1班 何小薇 女 83 65 8 9
7 80 六1班 雷旺 男 NA 68 8 9
8 80 六1班 陈欣越 男 57 60 9 9
9 NA 六1班 黄亦婷 女 77 54 8 10
10 55 六1班 陈媚 女 68 66 8 9
# … with 40 more rows
rolocate(.data, …, .before, .after):将选择的列移动到某列之前或之后
# A tibble: 50 × 8
class name chinese math english moral science sex
<chr> <chr> <dbl> <dbl> <dbl> <dbl> <dbl> <chr>
1 六1班 何娜 87 92 79 9 10 女
2 六1班 黄才菊 95 77 75 NA 9 女
3 六1班 陈芳妹 79 87 66 9 10 女
4 六1班 陈学勤 NA 79 66 9 10 男
5 六1班 陈祝贞 76 79 67 8 10 女
6 六1班 何小薇 83 73 65 8 9 女
7 六1班 雷旺 NA 80 68 8 9 男
8 六1班 陈欣越 57 80 60 9 9 男
9 六1班 黄亦婷 77 NA 54 8 10 女
10 六1班 陈媚 68 55 66 8 9 女
# … with 40 more rows
5.重命名列
set_name:为所有列设置新列名
# A tibble: 50 × 8
` 班级` ` 姓名` ` 性别` ` 语文` ` 数学` ` 英语` ` 品德` ` 科学`
<chr> <chr> <chr> <dbl> <dbl> <dbl> <dbl> <dbl>
1 六1班 何娜 女 87 92 79 9 10
2 六1班 黄才菊 女 95 77 75 NA 9
3 六1班 陈芳妹 女 79 87 66 9 10
4 六1班 陈学勤 男 NA 79 66 9 10
5 六1班 陈祝贞 女 76 79 67 8 10
6 六1班 何小薇 女 83 73 65 8 9
7 六1班 雷旺 男 NA 80 68 8 9
8 六1班 陈欣越 男 57 80 60 9 9
9 六1班 黄亦婷 女 77 NA 54 8 10
10 六1班 陈媚 女 68 55 66 8 9
# … with 40 more rows
rename():只修改部分列名,格式为:新名 = 旧名
# A tibble: 50 × 8
class name sex chinese 数学 english moral 科学
<chr> <chr> <chr> <dbl> <dbl> <dbl> <dbl> <dbl>
1 六1班 何娜 女 87 92 79 9 10
2 六1班 黄才菊 女 95 77 75 NA 9
3 六1班 陈芳妹 女 79 87 66 9 10
4 六1班 陈学勤 男 NA 79 66 9 10
5 六1班 陈祝贞 女 76 79 67 8 10
6 六1班 何小薇 女 83 73 65 8 9
7 六1班 雷旺 男 NA 80 68 8 9
8 六1班 陈欣越 男 57 80 60 9 9
9 六1班 黄亦婷 女 77 NA 54 8 10
10 六1班 陈媚 女 68 55 66 8 9
# … with 40 more rows
6.强大的across()函数
across()人如其名,让零个、一个、或多个函数穿过所选择的列即同时对选择的多列应用若干函数,基本格式为:
across(.cols = everything(), .fns = NULL, …, .name)
二、修改列
修改列,即修改数据框的列,计算新列
1.创建新列
mutate()创建或修改列,返回原数据框并增加新列,默认加在最后一列,参数.before, .after可以设置新列的位置
# A tibble: 50 × 9
class name sex new chinese math english moral science
<chr> <chr> <chr> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl>
1 六1班 何娜 女 5 87 92 79 9 10
2 六1班 黄才菊 女 5 95 77 75 NA 9
3 六1班 陈芳妹 女 5 79 87 66 9 10
4 六1班 陈学勤 男 5 NA 79 66 9 10
5 六1班 陈祝贞 女 5 76 79 67 8 10
6 六1班 何小薇 女 5 83 73 65 8 9
7 六1班 雷旺 男 5 NA 80 68 8 9
8 六1班 陈欣越 男 5 57 80 60 9 9
9 六1班 黄亦婷 女 5 77 NA 54 8 10
10 六1班 陈媚 女 5 68 55 66 8 9
# … with 40 more rows
正常是以长度等于行数的向量赋值:
# A tibble: 50 × 9
class new name sex chinese math english moral science
<chr> <int> <chr> <chr> <dbl> <dbl> <dbl> <dbl> <dbl>
1 六1班 1 何娜 女 87 92 79 9 10
2 六1班 2 黄才菊 女 95 77 75 NA 9
3 六1班 3 陈芳妹 女 79 87 66 9 10
4 六1班 4 陈学勤 男 NA 79 66 9 10
5 六1班 5 陈祝贞 女 76 79 67 8 10
6 六1班 6 何小薇 女 83 73 65 8 9
7 六1班 7 雷旺 男 NA 80 68 8 9
8 六1班 8 陈欣越 男 57 80 60 9 9
9 六1班 9 黄亦婷 女 77 NA 54 8 10
10 六1班 10 陈媚 女 68 55 66 8 9
# … with 40 more rows
2.计算新列
用数据框的现有列计算新列,若修改当前列,只需要赋值给原列名
# A tibble: 50 × 9
class name sex total chinese math english moral science
<chr> <chr> <chr> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl>
1 六1班 何娜 女 277 87 92 79 9 10
2 六1班 黄才菊 女 NA 95 77 75 NA 9
3 六1班 陈芳妹 女 251 79 87 66 9 10
4 六1班 陈学勤 男 NA NA 79 66 9 10
5 六1班 陈祝贞 女 240 76 79 67 8 10
6 六1班 何小薇 女 238 83 73 65 8 9
7 六1班 雷旺 男 NA NA 80 68 8 9
8 六1班 陈欣越 男 215 57 80 60 9 9
9 六1班 黄亦婷 女 NA 77 NA 54 8 10
10 六1班 陈媚 女 206 68 55 66 8 9
# … with 40 more rows
注意:不能用sum(),它会将整个列的内容都加起来,类似的还有mean()等
在同一个muatate()中可以同时创建或计算多个列,他们是从前往后依次计算,所以可以使用前面新创建的列
Code
# A tibble: 50 × 10
class name sex med label chinese math english moral science
<chr> <chr> <chr> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl>
1 六1班 何娜 女 73 1 87 92 79 9 10
2 六1班 黄才菊 女 73 1 95 77 75 NA 9
3 六1班 陈芳妹 女 73 1 79 87 66 9 10
4 六1班 陈学勤 男 73 1 NA 79 66 9 10
5 六1班 陈祝贞 女 73 1 76 79 67 8 10
6 六1班 何小薇 女 73 0 83 73 65 8 9
7 六1班 雷旺 男 73 1 NA 80 68 8 9
8 六1班 陈欣越 男 73 1 57 80 60 9 9
9 六1班 黄亦婷 女 73 NA 77 NA 54 8 10
10 六1班 陈媚 女 73 0 68 55 66 8 9
# … with 40 more rows
3.修改多列
结合across()和选择列语法可以应用函数到多列,从而实现同时修改多列。
(1)应用函数到所有列
将所有列转化为字符型
# A tibble: 50 × 8
class name sex chinese math english moral science
<chr> <chr> <chr> <chr> <chr> <chr> <chr> <chr>
1 六1班 何娜 女 87 92 79 9 10
2 六1班 黄才菊 女 95 77 75 <NA> 9
3 六1班 陈芳妹 女 79 87 66 9 10
4 六1班 陈学勤 男 <NA> 79 66 9 10
5 六1班 陈祝贞 女 76 79 67 8 10
6 六1班 何小薇 女 83 73 65 8 9
7 六1班 雷旺 男 <NA> 80 68 8 9
8 六1班 陈欣越 男 57 80 60 9 9
9 六1班 黄亦婷 女 77 <NA> 54 8 10
10 六1班 陈媚 女 68 55 66 8 9
# … with 40 more rows
(2)对所有数值列做归一化
Code
# A tibble: 50 × 8
class name sex chinese math english moral science
<chr> <chr> <chr> <dbl> <dbl> <dbl> <dbl> <dbl>
1 六1班 何娜 女 0.843 0.974 1 0.875 1
2 六1班 黄才菊 女 1 0.776 0.926 NA 0.833
3 六1班 陈芳妹 女 0.686 0.908 0.759 0.875 1
4 六1班 陈学勤 男 NA 0.803 0.759 0.875 1
5 六1班 陈祝贞 女 0.627 0.803 0.778 0.75 1
6 六1班 何小薇 女 0.765 0.724 0.741 0.75 0.833
7 六1班 雷旺 男 NA 0.816 0.796 0.75 0.833
8 六1班 陈欣越 男 0.255 0.816 0.648 0.875 0.833
9 六1班 黄亦婷 女 0.647 NA 0.537 0.75 1
10 六1班 陈媚 女 0.471 0.487 0.759 0.75 0.833
# … with 40 more rows
(3)应用函数到指定的列
将iris中的列名包含length和width的列的测量单位从厘米变成毫米
4.替换NA
(1)replace_na()
实现用某个值替换一列中的所有NA值,该函数接受一个命名列表,其成分为列名 = 替换值
替换具体的缺失值
# A tibble: 87 × 14
name height mass hair_…¹ skin_…² eye_c…³ birth…⁴ sex gender homew…⁵
<chr> <int> <dbl> <chr> <chr> <chr> <dbl> <chr> <chr> <chr>
1 Luke Skywa… 172 77 blond fair blue 19 male mascu… Tatooi…
2 C-3PO 167 75 hc gold yellow 112 none mascu… Tatooi…
3 R2-D2 96 32 hc white,… red 33 none mascu… Naboo
4 Darth Vader 202 136 none white yellow 41.9 male mascu… Tatooi…
5 Leia Organa 150 49 brown light brown 19 fema… femin… Aldera…
6 Owen Lars 178 120 brown,… light blue 52 male mascu… Tatooi…
7 Beru White… 165 75 brown light blue 47 fema… femin… Tatooi…
8 R5-D4 97 32 hc white,… red NA none mascu… Tatooi…
9 Biggs Dark… 183 84 black light brown 24 male mascu… Tatooi…
10 Obi-Wan Ke… 182 77 auburn… fair blue-g… 57 male mascu… Stewjon
# … with 77 more rows, 4 more variables: species <chr>, films <list>,
# vehicles <list>, starships <list>, and abbreviated variable names
# ¹hair_color, ²skin_color, ³eye_color, ⁴birth_year, ⁵homeworld
所有浮点列的缺失值用其均值替换:
# A tibble: 87 × 14
name height mass hair_…¹ skin_…² eye_c…³ birth…⁴ sex gender homew…⁵
<chr> <int> <dbl> <chr> <chr> <chr> <dbl> <chr> <chr> <chr>
1 Luke Skywa… 172 77 blond fair blue 19 male mascu… Tatooi…
2 C-3PO 167 75 <NA> gold yellow 112 none mascu… Tatooi…
3 R2-D2 96 32 <NA> white,… red 33 none mascu… Naboo
4 Darth Vader 202 136 none white yellow 41.9 male mascu… Tatooi…
5 Leia Organa 150 49 brown light brown 19 fema… femin… Aldera…
6 Owen Lars 178 120 brown,… light blue 52 male mascu… Tatooi…
7 Beru White… 165 75 brown light blue 47 fema… femin… Tatooi…
8 R5-D4 97 32 <NA> white,… red 87.6 none mascu… Tatooi…
9 Biggs Dark… 183 84 black light brown 24 male mascu… Tatooi…
10 Obi-Wan Ke… 182 77 auburn… fair blue-g… 57 male mascu… Stewjon
# … with 77 more rows, 4 more variables: species <chr>, films <list>,
# vehicles <list>, starships <list>, and abbreviated variable names
# ¹hair_color, ²skin_color, ³eye_color, ⁴birth_year, ⁵homeworld
(2)用前一个(或后一个)非缺失值填充NA
# A tibble: 87 × 14
name height mass hair_…¹ skin_…² eye_c…³ birth…⁴ sex gender homew…⁵
<chr> <int> <dbl> <chr> <chr> <chr> <dbl> <chr> <chr> <chr>
1 Luke Skywa… 172 77 blond fair blue 19 male mascu… Tatooi…
2 C-3PO 167 75 <NA> gold yellow 112 none mascu… Tatooi…
3 R2-D2 96 32 <NA> white,… red 33 none mascu… Naboo
4 Darth Vader 202 136 none white yellow 41.9 male mascu… Tatooi…
5 Leia Organa 150 49 brown light brown 19 fema… femin… Aldera…
6 Owen Lars 178 120 brown,… light blue 52 male mascu… Tatooi…
7 Beru White… 165 75 brown light blue 47 fema… femin… Tatooi…
8 R5-D4 97 32 <NA> white,… red NA none mascu… Tatooi…
9 Biggs Dark… 183 84 black light brown 24 male mascu… Tatooi…
10 Obi-Wan Ke… 182 77 auburn… fair blue-g… 57 male mascu… Stewjon
# … with 77 more rows, 4 more variables: species <chr>, films <list>,
# vehicles <list>, starships <list>, and abbreviated variable names
# ¹hair_color, ²skin_color, ³eye_color, ⁴birth_year, ⁵homeworld
5.重新编码
(1)两类别情形:if_else():做二分支判断进而重新编码
# A tibble: 50 × 8
class name sex chinese math english moral science
<chr> <chr> <chr> <dbl> <dbl> <dbl> <dbl> <dbl>
1 六1班 何娜 f 87 92 79 9 10
2 六1班 黄才菊 f 95 77 75 NA 9
3 六1班 陈芳妹 f 79 87 66 9 10
4 六1班 陈学勤 m NA 79 66 9 10
5 六1班 陈祝贞 f 76 79 67 8 10
6 六1班 何小薇 f 83 73 65 8 9
7 六1班 雷旺 m NA 80 68 8 9
8 六1班 陈欣越 m 57 80 60 9 9
9 六1班 黄亦婷 f 77 NA 54 8 10
10 六1班 陈媚 f 68 55 66 8 9
# … with 40 more rows
(2)多类别情形:case_when():做多分支判断进而重新编码,避免使用很多if_else()嵌套
# A tibble: 50 × 8
class name sex chinese math english moral science
<chr> <chr> <chr> <dbl> <chr> <dbl> <dbl> <dbl>
1 六1班 何娜 女 87 high 79 9 10
2 六1班 黄才菊 女 95 high 75 NA 9
3 六1班 陈芳妹 女 79 high 66 9 10
4 六1班 陈学勤 男 NA high 66 9 10
5 六1班 陈祝贞 女 76 high 67 8 10
6 六1班 何小薇 女 83 middle 65 8 9
7 六1班 雷旺 男 NA high 68 8 9
8 六1班 陈欣越 男 57 high 60 9 9
9 六1班 黄亦婷 女 77 low 54 8 10
10 六1班 陈媚 女 68 low 66 8 9
# … with 40 more rows
最后一个分支直接用TRUE表示若其他条件都不为TRUE时怎么做
(3)更强大的重新编码函数
sjmisc包提供了rec(x, rec, append, ….)基本实现了spss重新编码的功能-x:为数据框(或向量)
Code
math_r <character>
# total N=50 valid N=50 mean=3.28 sd=1.26
Value | N | Raw % | Valid % | Cum. %
--------------------------------------
-Inf | 3 | 6.00 | 6.00 | 6
不及格 | 14 | 28.00 | 28.00 | 34
良 | 10 | 20.00 | 20.00 | 54
优 | 12 | 24.00 | 24.00 | 78
中 | 11 | 22.00 | 22.00 | 100
<NA> | 0 | 0.00 | <NA> | <NA>