・はじめに
・複数処理
・複数条件
(最終更新2025/5/6)
私はあえて、dplyrパッケージを使ったコーディングをしてこなかった。むしろ、通常のコーディングのほうがわかりやすいと感じているからだ。そして、dplyr内でのデータフレームの扱いが、他の関数で使えない、みたいなこともたまに生じる。バグを避けるために、あえて使ってこなかった。とはいえ、最近は複雑な処理も増え、入れ子のコーディングとなると、わかりにくくなるのも事実である。コーディングの癖は、通常とdplyrで異なるので、個人的には可能な限りどちらかに統一する方が混乱が少ないと思う。ここでは、自分の勉強も込めて、通常コードとdplyrコードの書き換えを表記しておく。ただし、出力を完全に同じにする、というよりも相当するコード、という気持ちで見てほしい。
dplyrだけでなく、関連のパッケージをtidyverseパッケージをインストールすることで、一括取り込みできるので、活用しよう。
------------------------------------------------------
library(tidyverse)
------------------------------------------------------
今回は、デフォルトで利用可能なirisのデータセットを用いる。
------------------------------------------------------
head(iris)
## Sepal.Length Sepal.Width Petal.Length Petal.Width Species
## 1 5.1 3.5 1.4 0.2 setosa
## 2 4.9 3.0 1.4 0.2 setosa
## 3 4.7 3.2 1.3 0.2 setosa
## 4 4.6 3.1 1.5 0.2 setosa
## 5 5.0 3.6 1.4 0.2 setosa
## 6 5.4 3.9 1.7 0.4 setosa
------------------------------------------------------
まずは、通常コード
------------------------------------------------------
iris$Petal.Length
## [1] 1.4 1.4 1.3 1.5 1.4 1.7 1.4 1.5 1.4 1.5 1.5 1.6 1.4 1.1 1.2 1.5 1.3 1.4
## [19] 1.7 1.5 1.7 1.5 1.0 1.7 1.9 1.6 1.6 1.5 1.4 1.6 1.6 1.5 1.5 1.4 1.5 1.2
## [37] 1.3 1.4 1.3 1.5 1.3 1.3 1.3 1.6 1.9 1.4 1.6 1.4 1.5 1.4 4.7 4.5 4.9 4.0
## [55] 4.6 4.5 4.7 3.3 4.6 3.9 3.5 4.2 4.0 4.7 3.6 4.4 4.5 4.1 4.5 3.9 4.8 4.0
## [73] 4.9 4.7 4.3 4.4 4.8 5.0 4.5 3.5 3.8 3.7 3.9 5.1 4.5 4.5 4.7 4.4 4.1 4.0
## [91] 4.4 4.6 4.0 3.3 4.2 4.2 4.2 4.3 3.0 4.1 6.0 5.1 5.9 5.6 5.8 6.6 4.5 6.3
## [109] 5.8 6.1 5.1 5.3 5.5 5.0 5.1 5.3 5.5 6.7 6.9 5.0 5.7 4.9 6.7 4.9 5.7 6.0
## [127] 4.8 4.9 5.6 5.8 6.1 6.4 5.6 5.1 5.6 6.1 5.6 5.5 4.8 5.4 5.6 5.1 5.1 5.9
## [145] 5.7 5.2 5.0 5.2 5.4 5.1
iris[, "Petal.Length"]
## [1] 1.4 1.4 1.3 1.5 1.4 1.7 1.4 1.5 1.4 1.5 1.5 1.6 1.4 1.1 1.2 1.5 1.3 1.4
## [19] 1.7 1.5 1.7 1.5 1.0 1.7 1.9 1.6 1.6 1.5 1.4 1.6 1.6 1.5 1.5 1.4 1.5 1.2
## [37] 1.3 1.4 1.3 1.5 1.3 1.3 1.3 1.6 1.9 1.4 1.6 1.4 1.5 1.4 4.7 4.5 4.9 4.0
## [55] 4.6 4.5 4.7 3.3 4.6 3.9 3.5 4.2 4.0 4.7 3.6 4.4 4.5 4.1 4.5 3.9 4.8 4.0
## [73] 4.9 4.7 4.3 4.4 4.8 5.0 4.5 3.5 3.8 3.7 3.9 5.1 4.5 4.5 4.7 4.4 4.1 4.0
## [91] 4.4 4.6 4.0 3.3 4.2 4.2 4.2 4.3 3.0 4.1 6.0 5.1 5.9 5.6 5.8 6.6 4.5 6.3
## [109] 5.8 6.1 5.1 5.3 5.5 5.0 5.1 5.3 5.5 6.7 6.9 5.0 5.7 4.9 6.7 4.9 5.7 6.0
## [127] 4.8 4.9 5.6 5.8 6.1 6.4 5.6 5.1 5.6 6.1 5.6 5.5 4.8 5.4 5.6 5.1 5.1 5.9
## [145] 5.7 5.2 5.0 5.2 5.4 5.1
------------------------------------------------------
dplyrコード。ただし、何も指定しないと、全件表示されるので、こっちで切っている。
------------------------------------------------------
select(iris, Petal.Length)
## Petal.Length
## 1 1.4
## 2 1.4
## 3 1.3
## 4 1.5
## 5 1.4
## 6 1.7
------------------------------------------------------
dplyrコードでは、パイプ演算子%>%を多用する。パイプ演算子は、「直前の処理したオブジェクトを次の関数に受け渡す役割」を担っている。受け渡し方は次の2つのルールを覚えておくとよい。
1. 何も指定がない場合、次の関数の第1引数にオブジェクトを渡す。
2. 第1引数以外に渡したい場合は、「引数 = .」という形でその引数にオブジェクトを渡す。
例えば、以下の通り。
------------------------------------------------------
iris %>% select(Petal.Length)
## Petal.Length
## 1 1.4
## 2 1.4
## 3 1.3
## 4 1.5
## 5 1.4
## 6 1.7
------------------------------------------------------
Petal.Lengthというオブジェクトを定義したわけではないのに、このスクリプトは動く。というのは、うえの処理はselect(iris, Petal.Length)と同等である。select関数の第1引数は.dataであり、データフレームをとる。パイプ演算子によって、第1引数.dataにirisを代入して計算が行われている、ということになる。以下のようなスクリプトでもよい。
------------------------------------------------------
iris %>% select(., Petal.Length)
## Petal.Length
## 1 1.4
## 2 1.4
## 3 1.3
## 4 1.5
## 5 1.4
## 6 1.7
------------------------------------------------------
この場合、.=irisということを意味する。ピリオドを利用すれば、任意の引数に直前のオブジェクトを代入できる。試しに、iris %>% select(Petal.Length, .data = .)としても実行可能であることが確認できるだろう。
ちなみに、通常コードと出力が違うが、もしあえてそろえるとしたら、以下のような方法がある。
------------------------------------------------------
iris %>% select(Petal.Length) %>% unlist(use.names = F)
## [1] 1.4 1.4 1.3 1.5 1.4 1.7 1.4 1.5 1.4 1.5 1.5 1.6 1.4 1.1 1.2 1.5 1.3 1.4
## [19] 1.7 1.5 1.7 1.5 1.0 1.7 1.9 1.6 1.6 1.5 1.4 1.6 1.6 1.5 1.5 1.4 1.5 1.2
## [37] 1.3 1.4 1.3 1.5 1.3 1.3 1.3 1.6 1.9 1.4 1.6 1.4 1.5 1.4 4.7 4.5 4.9 4.0
## [55] 4.6 4.5 4.7 3.3 4.6 3.9 3.5 4.2 4.0 4.7 3.6 4.4 4.5 4.1 4.5 3.9 4.8 4.0
## [73] 4.9 4.7 4.3 4.4 4.8 5.0 4.5 3.5 3.8 3.7 3.9 5.1 4.5 4.5 4.7 4.4 4.1 4.0
## [91] 4.4 4.6 4.0 3.3 4.2 4.2 4.2 4.3 3.0 4.1 6.0 5.1 5.9 5.6 5.8 6.6 4.5 6.3
## [109] 5.8 6.1 5.1 5.3 5.5 5.0 5.1 5.3 5.5 6.7 6.9 5.0 5.7 4.9 6.7 4.9 5.7 6.0
## [127] 4.8 4.9 5.6 5.8 6.1 6.4 5.6 5.1 5.6 6.1 5.6 5.5 4.8 5.4 5.6 5.1 5.1 5.9
## [145] 5.7 5.2 5.0 5.2 5.4 5.1
------------------------------------------------------
これは、iris %>% select(Petal.Length)までの処理を、unlist(use.names = F)の第1引数、xに代入している。
まずは、通常コード
------------------------------------------------------
iris[,1:3]
## Sepal.Length Sepal.Width Petal.Length
## 1 5.1 3.5 1.4
## 2 4.9 3.0 1.4
## 3 4.7 3.2 1.3
## 4 4.6 3.1 1.5
## 5 5.0 3.6 1.4
## 6 5.4 3.9 1.7
------------------------------------------------------
dplyrコード。通常コードと同様、数字を使った指定が可能である。
------------------------------------------------------
select(iris, 1:3)
## Sepal.Length Sepal.Width Petal.Length
## 1 5.1 3.5 1.4
## 2 4.9 3.0 1.4
## 3 4.7 3.2 1.3
## 4 4.6 3.1 1.5
## 5 5.0 3.6 1.4
## 6 5.4 3.9 1.7
------------------------------------------------------
列名を:で結んでも取り出せる。地味に便利な操作だ。
------------------------------------------------------
select(iris, Sepal.Length:Petal.Length)
## Sepal.Length Sepal.Width Petal.Length
## 1 5.1 3.5 1.4
## 2 4.9 3.0 1.4
## 3 4.7 3.2 1.3
## 4 4.6 3.1 1.5
## 5 5.0 3.6 1.4
## 6 5.4 3.9 1.7
------------------------------------------------------
もちろん、パイプ演算子を使ってもよい。
------------------------------------------------------
iris %>% select(1:3)
## Sepal.Length Sepal.Width Petal.Length
## 1 5.1 3.5 1.4
## 2 4.9 3.0 1.4
## 3 4.7 3.2 1.3
## 4 4.6 3.1 1.5
## 5 5.0 3.6 1.4
## 6 5.4 3.9 1.7
------------------------------------------------------
まずは、通常コード
------------------------------------------------------
iris[1:3,]
## Sepal.Length Sepal.Width Petal.Length Petal.Width Species
## 1 5.1 3.5 1.4 0.2 setosa
## 2 4.9 3.0 1.4 0.2 setosa
## 3 4.7 3.2 1.3 0.2 setosa
------------------------------------------------------
dplyrコード。この時は、slice関数を用いる。パイプ演算子も用いることが可能である。
------------------------------------------------------
slice(iris, 1:3)
## Sepal.Length Sepal.Width Petal.Length Petal.Width Species
## 1 5.1 3.5 1.4 0.2 setosa
## 2 4.9 3.0 1.4 0.2 setosa
## 3 4.7 3.2 1.3 0.2 setosa
iris %>% slice(1:3)
## Sepal.Length Sepal.Width Petal.Length Petal.Width Species
## 1 5.1 3.5 1.4 0.2 setosa
## 2 4.9 3.0 1.4 0.2 setosa
## 3 4.7 3.2 1.3 0.2 setosa
------------------------------------------------------
まずは、通常コード
------------------------------------------------------
iris[iris$Sepal.Length > 5,]
## Sepal.Length Sepal.Width Petal.Length Petal.Width Species
## 1 5.1 3.5 1.4 0.2 setosa
## 6 5.4 3.9 1.7 0.4 setosa
## 11 5.4 3.7 1.5 0.2 setosa
## 15 5.8 4.0 1.2 0.2 setosa
## 16 5.7 4.4 1.5 0.4 setosa
## 17 5.4 3.9 1.3 0.4 setosa
------------------------------------------------------
dplyrコード。この時は、filter関数を用いる。slice関数ではないので注意しよう。パイプ演算子も用いることが可能である。
------------------------------------------------------
filter(iris, Sepal.Length > 5)
## Sepal.Length Sepal.Width Petal.Length Petal.Width Species
## 1 5.1 3.5 1.4 0.2 setosa
## 2 5.4 3.9 1.7 0.4 setosa
## 3 5.4 3.7 1.5 0.2 setosa
## 4 5.8 4.0 1.2 0.2 setosa
## 5 5.7 4.4 1.5 0.4 setosa
## 6 5.4 3.9 1.3 0.4 setosa
iris %>% filter(Sepal.Length > 5)
## Sepal.Length Sepal.Width Petal.Length Petal.Width Species
## 1 5.1 3.5 1.4 0.2 setosa
## 2 5.4 3.9 1.7 0.4 setosa
## 3 5.4 3.7 1.5 0.2 setosa
## 4 5.8 4.0 1.2 0.2 setosa
## 5 5.7 4.4 1.5 0.4 setosa
## 6 5.4 3.9 1.3 0.4 setosa
------------------------------------------------------
さて、ここまでは単独の処理を書き換えたものであるため、ありがたみは少ない。しかし、dplyrの真価は複数の処理を行ったときに、コードの見通しをよくする点にある。
例えば、通常コードで特定の条件に合う行を取り出し、さらにその行に関して列を取り出すとする。
------------------------------------------------------
iris[iris$Sepal.Length > 5, "Petal.Length"]
## [1] 1.4 1.7 1.5 1.2 1.5 1.3 1.4 1.7 1.5 1.7 1.5 1.7 1.5 1.4 1.5 1.5 1.4 1.3
## [19] 1.5 1.9 1.6 1.5 4.7 4.5 4.9 4.0 4.6 4.5 4.7 4.6 3.9 4.2 4.0 4.7 3.6 4.4
## [37] 4.5 4.1 4.5 3.9 4.8 4.0 4.9 4.7 4.3 4.4 4.8 5.0 4.5 3.5 3.8 3.7 3.9 5.1
## [55] 4.5 4.5 4.7 4.4 4.1 4.0 4.4 4.6 4.0 4.2 4.2 4.2 4.3 3.0 4.1 6.0 5.1 5.9
## [73] 5.6 5.8 6.6 6.3 5.8 6.1 5.1 5.3 5.5 5.0 5.1 5.3 5.5 6.7 6.9 5.0 5.7 4.9
## [91] 6.7 4.9 5.7 6.0 4.8 4.9 5.6 5.8 6.1 6.4 5.6 5.1 5.6 6.1 5.6 5.5 4.8 5.4
## [109] 5.6 5.1 5.1 5.9 5.7 5.2 5.0 5.2 5.4 5.1
iris[iris$Sepal.Length > 5, ]$Petal.Length
## [1] 1.4 1.7 1.5 1.2 1.5 1.3 1.4 1.7 1.5 1.7 1.5 1.7 1.5 1.4 1.5 1.5 1.4 1.3
## [19] 1.5 1.9 1.6 1.5 4.7 4.5 4.9 4.0 4.6 4.5 4.7 4.6 3.9 4.2 4.0 4.7 3.6 4.4
## [37] 4.5 4.1 4.5 3.9 4.8 4.0 4.9 4.7 4.3 4.4 4.8 5.0 4.5 3.5 3.8 3.7 3.9 5.1
## [55] 4.5 4.5 4.7 4.4 4.1 4.0 4.4 4.6 4.0 4.2 4.2 4.2 4.3 3.0 4.1 6.0 5.1 5.9
## [73] 5.6 5.8 6.6 6.3 5.8 6.1 5.1 5.3 5.5 5.0 5.1 5.3 5.5 6.7 6.9 5.0 5.7 4.9
## [91] 6.7 4.9 5.7 6.0 4.8 4.9 5.6 5.8 6.1 6.4 5.6 5.1 5.6 6.1 5.6 5.5 4.8 5.4
## [109] 5.6 5.1 5.1 5.9 5.7 5.2 5.0 5.2 5.4 5.1
------------------------------------------------------
dplyrコードでは、以下のように処理できる。どの処理を行ったか、明確になる。
------------------------------------------------------
iris %>% filter(Sepal.Length > 5) %>% select(Petal.Length)
## Petal.Length
## 1 1.4
## 2 1.7
## 3 1.5
## 4 1.2
## 5 1.5
## 6 1.3
------------------------------------------------------
もっと複雑な処理をしてみよう。通常コードは以下の場合だ。
------------------------------------------------------
iris[iris$Sepal.Length > 5 & iris$Sepal.Width < 3,
c("Petal.Length", "Petal.Width")]
## Petal.Length Petal.Width
## 54 4.0 1.3
## 55 4.6 1.5
## 56 4.5 1.3
## 59 4.6 1.3
## 60 3.9 1.4
## 63 4.0 1.0
------------------------------------------------------
dplyrコードでは、以下のように処理できる。
------------------------------------------------------
iris %>%
filter(Sepal.Length > 5 & Sepal.Width < 3) %>%
select(Petal.Length, Petal.Width)
## Petal.Length Petal.Width
## 1 4.0 1.3
## 2 4.6 1.5
## 3 4.5 1.3
## 4 4.6 1.3
## 5 3.9 1.4
## 6 4.0 1.0
------------------------------------------------------
処理が入れ子になる場合も見通しが良くなる。通常コードは以下の場合だ。
------------------------------------------------------
length(
unique(
iris[iris$Sepal.Length > 5 & iris$Sepal.Width < 3,
"Petal.Length"]
)
)
## [1] 25
------------------------------------------------------
dplyrコードでは、以下のように処理できる。
------------------------------------------------------
iris %>%
filter(Sepal.Length > 5) %>%
filter(Sepal.Width < 3) %>%
#&ならパイプでつなげ続けてよい
select(Petal.Length) %>%
unique() %>%
nrow()
## [1] 25
------------------------------------------------------
データフレームの加工において、何か処理を終えた列をもとのデータフレームに追加したいこともあるだろう。例えば、2つの列の和を追加したい場合などだ。通常コードでは以下のようにするだろう。
------------------------------------------------------
iris$SLplusSW <- iris$Sepal.Length + iris$Sepal.Width
head(iris)
## Sepal.Length Sepal.Width Petal.Length Petal.Width Species SLplusSW
## 1 5.1 3.5 1.4 0.2 setosa 8.6
## 2 4.9 3.0 1.4 0.2 setosa 7.9
## 3 4.7 3.2 1.3 0.2 setosa 7.9
## 4 4.6 3.1 1.5 0.2 setosa 7.7
## 5 5.0 3.6 1.4 0.2 setosa 8.6
## 6 5.4 3.9 1.7 0.4 setosa 9.3
rm(iris) #新たなオブジェクトが追加されるのでいったん削除
------------------------------------------------------
dplyrコードでは、以下のようにmutate関数を用いることで元のデータフレームに列を追加できる。
------------------------------------------------------
mutate(iris, SLplusSW = Sepal.Length + Sepal.Width) %>% head()
## Sepal.Length Sepal.Width Petal.Length Petal.Width Species SLplusSW
## 1 5.1 3.5 1.4 0.2 setosa 8.6
## 2 4.9 3.0 1.4 0.2 setosa 7.9
## 3 4.7 3.2 1.3 0.2 setosa 7.9
## 4 4.6 3.1 1.5 0.2 setosa 7.7
## 5 5.0 3.6 1.4 0.2 setosa 8.6
## 6 5.4 3.9 1.7 0.4 setosa 9.3
iris %>%
mutate(SLplusSW = Sepal.Length + Sepal.Width) %>%
head()
## Sepal.Length Sepal.Width Petal.Length Petal.Width Species SLplusSW
## 1 5.1 3.5 1.4 0.2 setosa 8.6
## 2 4.9 3.0 1.4 0.2 setosa 7.9
## 3 4.7 3.2 1.3 0.2 setosa 7.9
## 4 4.6 3.1 1.5 0.2 setosa 7.7
## 5 5.0 3.6 1.4 0.2 setosa 8.6
## 6 5.4 3.9 1.7 0.4 setosa 9.3
------------------------------------------------------
行の並べ替えも行うことができる。通常コードでは以下の通り。
------------------------------------------------------
iris[order(iris$Sepal.Length),]
## Sepal.Length Sepal.Width Petal.Length Petal.Width Species
## 14 4.3 3.0 1.1 0.1 setosa
## 9 4.4 2.9 1.4 0.2 setosa
## 39 4.4 3.0 1.3 0.2 setosa
## 43 4.4 3.2 1.3 0.2 setosa
## 42 4.5 2.3 1.3 0.3 setosa
## 4 4.6 3.1 1.5 0.2 setosa
iris[order(iris$Sepal.Length, iris$Sepal.Width),]
## Sepal.Length Sepal.Width Petal.Length Petal.Width Species
## 14 4.3 3.0 1.1 0.1 setosa
## 9 4.4 2.9 1.4 0.2 setosa
## 39 4.4 3.0 1.3 0.2 setosa
## 43 4.4 3.2 1.3 0.2 setosa
## 42 4.5 2.3 1.3 0.3 setosa
## 4 4.6 3.1 1.5 0.2 setosa
------------------------------------------------------
dplyrコードでは、以下のようにarrange関数を用いることで元のデータフレームの行を並べ替えることができる。
------------------------------------------------------
iris %>% arrange(Sepal.Length)
## Sepal.Length Sepal.Width Petal.Length Petal.Width Species
## 1 4.3 3.0 1.1 0.1 setosa
## 2 4.4 2.9 1.4 0.2 setosa
## 3 4.4 3.0 1.3 0.2 setosa
## 4 4.4 3.2 1.3 0.2 setosa
## 5 4.5 2.3 1.3 0.3 setosa
## 6 4.6 3.1 1.5 0.2 setosa
iris %>% arrange(Sepal.Length, Sepal.Width)
## Sepal.Length Sepal.Width Petal.Length Petal.Width Species
## 1 4.3 3.0 1.1 0.1 setosa
## 2 4.4 2.9 1.4 0.2 setosa
## 3 4.4 3.0 1.3 0.2 setosa
## 4 4.4 3.2 1.3 0.2 setosa
## 5 4.5 2.3 1.3 0.3 setosa
## 6 4.6 3.1 1.5 0.2 setosa
------------------------------------------------------
通常コードでは以下の通り。
------------------------------------------------------
colnames(iris)[2] <- "tmp"
head(iris)
## Sepal.Length tmp Petal.Length Petal.Width Species SLplusSW
## 1 5.1 3.5 1.4 0.2 setosa 8.6
## 2 4.9 3.0 1.4 0.2 setosa 7.9
## 3 4.7 3.2 1.3 0.2 setosa 7.9
## 4 4.6 3.1 1.5 0.2 setosa 7.7
## 5 5.0 3.6 1.4 0.2 setosa 8.6
## 6 5.4 3.9 1.7 0.4 setosa 9.3
rm(iris)
------------------------------------------------------
dplyrコードでは、以下のようにrename関数を用いることで列名を変更できる。ただし、間違えやすいのが、コードを書くときは、変更後 = 変更前で表記する点である。代入するものを後から各癖があると、変更前 = 変更後と書きがちなので注意。
------------------------------------------------------
rename(iris, tmp = Sepal.Width) %>% head()
## Sepal.Length tmp Petal.Length Petal.Width Species
## 1 5.1 3.5 1.4 0.2 setosa
## 2 4.9 3.0 1.4 0.2 setosa
## 3 4.7 3.2 1.3 0.2 setosa
## 4 4.6 3.1 1.5 0.2 setosa
## 5 5.0 3.6 1.4 0.2 setosa
## 6 5.4 3.9 1.7 0.4 setosa
iris %>% rename(tmp = Sepal.Width) %>% head()
## Sepal.Length tmp Petal.Length Petal.Width Species
## 1 5.1 3.5 1.4 0.2 setosa
## 2 4.9 3.0 1.4 0.2 setosa
## 3 4.7 3.2 1.3 0.2 setosa
## 4 4.6 3.1 1.5 0.2 setosa
## 5 5.0 3.6 1.4 0.2 setosa
## 6 5.4 3.9 1.7 0.4 setosa
------------------------------------------------------
統計処理なども、グループごとにまとめて行うことができる。例えば、種ごとにPetal.Widthの平均をとるとすれば、通常コードではtapply関数を使うだろう。
------------------------------------------------------
tapply(iris$Petal.Width, iris$Species, mean)
## setosa versicolor virginica
## 0.246 1.326 2.026
------------------------------------------------------
dplyrコードでは、データフレームをgroup_by関数に渡した後、summarize関数に渡す。group_by関数は、指定された引数に基づいてグループ情報をデータフレームに付与する関数である。以下の例では「以降のsummarize関数では、Speciesごとに処理を行うように」という指示書を付けた形になる。
summarize関数は、summarize(計算結果を格納する列名 = 処理関数(処理列))という形で、group_byされたデータフレームを受け取る。以下の例では、新しい列名をmeanとしSpeciesごとにPetal.Widthをmean関数処理したものを返している。
------------------------------------------------------
iris %>%
group_by(Species) %>%
summarise(mean = mean(Petal.Width))
## # A tibble: 3 x 2
## Species mean
## <fct> <dbl>
## 1 setosa 0.246
## 2 versicolor 1.33
## 3 virginica 2.03
------------------------------------------------------
なお、同時に複数の計算をすることも可能である。例えば以下では、上記の平均のほか、Petal.Lengthをsd関数処理、Sepal.Widthをlength関数処理(要はこれは要素数)したものを同時に計算させている。
------------------------------------------------------
iris %>%
group_by(Species) %>%
summarise(mean = mean(Petal.Width),
sd = sd(Petal.Length),
n = length(Sepal.Width))
## # A tibble: 3 x 4
## Species mean sd n
## <fct> <dbl> <dbl> <int>
## 1 setosa 0.246 0.174 50
## 2 versicolor 1.33 0.470 50
## 3 virginica 2.03 0.552 50
------------------------------------------------------
また、要素数の取得としてlength関数を用いたが、要素数の取得であればlength関数の中身の列はどこでもよいはずだ。そこで、あえて列名を指定せずに要素数を取得する関数としてn()関数が用意されている。この関数は特殊で、group_by関数などで処理されたデータフレームを、summarize関数やfilter関数内などでしか受け取らない。以下のように使う。
------------------------------------------------------
iris %>%
group_by(Species) %>%
summarise(mean = mean(Petal.Width),
sd = sd(Petal.Length),
n = n())
## # A tibble: 3 x 4
## Species mean sd n
## <fct> <dbl> <dbl> <int>
## 1 setosa 0.246 0.174 50
## 2 versicolor 1.33 0.470 50
## 3 virginica 2.03 0.552 50
------------------------------------------------------