R實戰 第六篇:數據變換(aggregate+dplyr)


數據分析的工作,80%的時間耗費在處理數據上,而數據處理的主要過程可以分為:分離-操作-結合(Split-Apply-Combine),也就是說,首先,把數據根據特定的字段分組,每個分組都是獨立的;然后,對每個分組按照業務需求執行轉換;最后,把轉換后的結果組合在一起。在數據處理中,經常需要循環訪問數據,R語言是矢量化的,天生具有處理循環操作的優勢。

使用ggplot2包中的diamonds數據集做為示例數據

> install.packages('ggplot2')
> library(ggplot2) > data("diamonds")

data()函數的作用是加載指定的數據集,本例將加載ggplot2包中的diamonds數據集,這個數據集在下文直接引用。

一,使用aggregate()函數做數據變換

在研究數據時,有時需要對數據按照特定的字段進行分組,然后統計各個分組的數據,這就是SQL語法中的分組-聚合操作,使用aggregate()函數對數據進行簡單的數據處理。

aggregate()函數用於把數據分離為單獨的子集,為每一個子集計算聚合值,然后把聚合值結合(combine)在一起返回。

aggregate(formula, data, FUN, ...,subset, na.action = na.omit)

參數注釋:

  • formula:指定formula對象,包括符號“ ~”,以及在符號“~”兩側的變量,左側代表要計算聚合值的變量(聚合變量),右側代表分組的變量,例如,price~cut,函數依據分組變量,把數據分離為多個單獨的子集。
  • data:指定操作的數據框;
  • FUN:該參數用於指定函數,該函數應用在符號“~”左側的變量;
  • ...:指定傳遞給FUN函數的其他參數;
  • subset:向量類型,可選參數,用於指定data的觀測子集;
  • na.action: 如何處理缺失值,默認為忽略NA。如果不選擇na.omit,則需指定函數去處理NA。

1,單個分組變量

使用aggregate() 函數操作diamonds數據集,按照cut字段分組,函數mean的作用是為每個分組計算prince的平均值:

aggregate(price~cut,diamonds,mean)

2,多個分組變量

aggregate()函數能夠添加多個分組變量,只需要在formula右側添加變量,並用加號“+”隔離:

> aggregate(price~cut+color,diamonds,mean)
         cut color    price
1       Fair     D 4291.061
2       Good     D 3405.382
3  Very Good     D 3470.467
....

3,多個聚合變量

aggregate()函數能夠添加多個聚合變量,只需要在formula左側,使用函數cbind()把兩個變量組合起來:

> aggregate(cbind(price,carat)~cut,diamonds,mean)
        cut    price     carat
1      Fair 4358.758 1.0461366
2      Good 3928.864 0.8491847
3 Very Good 3981.760 0.8063814
4   Premium 4584.258 0.8919549
5     Ideal 3457.542 0.7028370

4,多個分組變量和多個聚合變量

aggregate()函數能夠formular對象的兩側分別添加多個變量,按照多個分組變量和多個聚合變量執行聚合運算

> aggregate(cbind(price,carat)~cut+color,diamonds,mean)
         cut color    price     carat
1       Fair     D 4291.061 0.9201227
2       Good     D 3405.382 0.7445166
....

二,計數

R中計數比較特殊,plyr包中有一個計算函數count(),參數vars定義分組的變量,該函數會把重復值計算N次:

count(df, vars = NULL)

使用aggregate()來實現分組計數,使用length(x)來計算向量中元素的個數,該函數會把重復值計算N次:

aggregate(cut~color,diamonds,length)

為了計算唯一值的數量,可以使用unique(x),在計數之前,對向量元素去重:

aggregate(cut~color,diamonds,function(x) length(unique(x)))

三,數據變換(dplyr包)

dplyr包提供靈活的數據操作,用於對數據框執行轉化和重塑,這個包是plyr包的升級版本,側重於處理數據框對象,因此其名字帶d(data frame),dplyr包是R開發人員必學必會的包。

dplyr包有三個主要的目標:

  •  更加靈活和簡單地處理數據框;
  • 使用內存,提高數據處理的性能;
  • 使用相同的接口處理數據,無論數據存儲在何處,無論是在數據框中,數據表或數據庫。
1,tlb類型
dplyr包不是默認安裝的包,在使用之前,需要使用以下命令安裝和引用dplyr包:
install.packages("dplyr")
library(dplyr)

dplyr包只能用於tibble(簡稱tbl)類型的對象,tibble 類型是dplyr包特有的對象類型(data frame tbl / tbl_df)。在利用dplyr包處理數據之前,建議把數據框裝載成tibble類型,可以調用 tbl_df()函數把數據框類型轉化成 tibble 類型的數據對象:

> df <- tbl_df(diamonds)

2,投影函數(select)

從tbl對象中,選擇特定的數據列顯示,select()函數的第一個參數是tibble對象,后續的參數是tbl對象中的變量名:

> select(df,carat,cut,color)

2,篩選函數(filter)

從tbl對象中,按照特定的條件過濾數據:

> filter(df,color=='E')

3,轉換函數(mutate)

根據tbl對象中的數據,應用指定的公式,派生新的數據列,或重寫已經存在的數據列:

> mutate(df,avg_ct=price/carat)

4,匯總函數(summarize)

對tbl對象執行聚合運算,如果tbl對象已經被分組,那么單獨對每個分組進行聚合運算:

> summarize(df,avg_prince=mean(price),avg_ct=mean(carat))

5,分組函數(group_by)和移除分組(ungroup)

使用group_by()函數對tbl對象執行分組,被分組之后,tbl對象處於分組狀態,可以使用ungroup函數,移除tbl對象的分組狀態。

group_by(df,color)

6,排序函數(arrange)

arrange()函數對tbl變量進行排序,默認是按照字段的升序值排序,使用desc(field),可以按照字段的降序值排序:

> arrange(df,color)

7,管道操作符(%>%)

管道操作符(%>%)用於把前一步操作的結果集(變量類型是tbl)傳遞到給函數的第一個參數中,同時函數的第一個參數可以省略,例如:

> df %>% group_by(color) %>% summarize(mean(price))
# A tibble: 7 x 2
  color `mean(price)`
  <ord>         <dbl>
1     D      3169.954
2     E      3076.752
3     F      3724.886
4     G      3999.136
5     H      4486.669
6     I      5091.875
7     J      5323.818

8,連接操作(join)

dplyr包還提供了連接(join)操作,

inner_join(x, y, by = NULL, copy = FALSE, suffix = c(".x", ".y"), ...)
left_join(x, y, by = NULL, copy = FALSE, suffix = c(".x", ".y"), ...)
right_join(x, y, by = NULL, copy = FALSE, suffix = c(".x", ".y"), ...)
full_join(x, y, by = NULL, copy = FALSE, suffix = c(".x", ".y"), ...)
semi_join(x, y, by = NULL, copy = FALSE, ...)
anti_join(x, y, by = NULL, copy = FALSE, ...)

參數注釋:

  • by:設置兩個數據集用於匹配的字段名,默認使用全部的同名字段進行匹配,如果兩個數據集需要匹配的字段名不同,可以直接用等號指定匹配的字段名,例如, by = c("a" = "b"),表示用x.a和y.b進行匹配。
  • copy:如果兩個數據集來自不同的數據源,copy設置為TRUE時,會把數據集y的數據復制到數據集x中,出於性能上的考慮,需要謹慎設置copy參數為TRUE。
  • suffix:合並后的數據集中同名變量,會自動添加suffix中設置的后綴加以區分。

9,集合操作(set)

#取兩個集合的交集
intersect(x,y, ...)

#取兩個集合的並集,並進行去重
union(x,y, ...)

#取兩個集合的並集,不去重
union_all(x,y, ...)

#取兩個集合的差集
setdiff(x,y, ...)

#判斷兩個集合是否相等
setequal(x, y, ...)

10,綁定操作

dplyr包提供了按行/列合並數據集的函數,合並的對象為數據框,也可以是能夠轉換為數據框的列表。按行合並函數bind_rows()通過列名進行匹配,不匹配的值使用NA替代,類似於base:: rbind()函數。按列合並函數bind_cols()通過行號匹配,因此合並的數據框必須有相同的行數,函數類似於base:: cbind()函數。原數據集行名稱會被過濾掉。

#按行合並,.id添加新列用於指明合並后每條數據來自的源數據框
bind_rows(...,.id = NULL)

#按列合並
bind_cols(...)

#合並數據集
combine(...)

11,排名操作

row_number(x)
ntile(x, n)
min_rank(x)
dense_rank(x)
percent_rank(x)
cume_dist(x)

例如,對一個向量的元素進行排序:

x <- c(5, 1, 3, 2, 2, NA)
row_number(x)

12,去重

對數據對象去重

distinct(data, ..., keep_all = FALSE)

參數注釋:

  • data:tbl對象
  • ... :可選的變量,用於指定去重的變量,如果去重的變量不唯一,那么只保留第一個觀測
  • keep_all:設置為TRUE時,所有的變量都保留到.data,如果...的組合不唯一,那么只保留第一行的觀測的各個變量值

13,計數

計數使用函數 n() 來實現,而統計數據集中無重復值的數量使用函數 n_distinct()來實現:

n()
n_distinct(..., na.rm = FALSE)

統計各個分組的觀測數量,只能用於 summarise(), mutate() 和 filter() 中

carriers <- group_by(flights, carrier)
summarise(carriers, n())
mutate(carriers, n = n())
filter(carriers, n() < 100)

 

參考文檔:

【R語言】必學包之dplyr包

R語言滴水穿石系列文章(一):dplyr-高效的數據變換與整理工具

R語言擴展包dplyr筆記

R: 矩陣運算及常用函數 II - aggregate


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM