標本の分布をRのggplotで描く

## 目標
こんな図をRで書けるようになります。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/518682/ea55abcb-994c-40ca-1751-ae97480a5d8e.png)

## データフレームの用意

標本の分布を描くにはデータフレームの準備が必要です。例えば次のようなデータを持っていたとします。
```
X <- c(1,2,3,4,5)
Y <- c(6,7,8,9,10)
Z <- c(11,12,13,14,15)
X
[1] 1 2 3 4 5
Y
[1]  6  7  8  9 10
Z
[1] 11 12 13 14 15
```
簡単に箱ひげ図（ボックスプロット）が書けます。
```
boxplot(X, Y, Z, names=c("X","Y","Z"))
```
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/518682/286d3809-d057-f54e-f69c-fa8e73845169.png)
標本のグループ数が、4個、5個と増えていくと長くなって大変なので、データフレームにするのが基本です。また、今後使うggplotでは、基本的にデータフレームです。
```
value <- c(X, Y, Z) # 3つのグループを結合させる
value
 [1]  1  2  3  4  5  6  7  8  9 10 11 12 13 14 15
group <- c(rep("X",5), rep("Y",5), rep("Z",5)) # valueが対応するグループ情報を作る
group
 [1] "X" "X" "X" "X" "X" "Y" "Y" "Y" "Y" "Y" "Z" "Z" "Z" "Z" "Z"
dat <- data.frame(value,group) # データフレームを作成
dat
   value group
1      1     X
2      2     X
3      3     X
4      4     X
5      5     X
6      6     Y
7      7     Y
8      8     Y
9      9     Y
10    10     Y
11    11     Z
12    12     Z
13    13     Z
14    14     Z
15    15     Z
```
これで値とグループの情報がひとまとめになったデータフレーム`dat`ができました。これを使ってふたたびボックスプロットを書きます。
```
boxplot(value~group, data=dat)
```
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/518682/f18f8013-9ed3-e692-8de3-3ac6f0ff5d67.png)
同じボックスプロットが書けました。`value~group`はgroupの情報に分けてvalueでボックスプロットを書けという意味の式です。`data=`で使用するデータフレームを指定します。

## 使用する標本データ

今回はRに組み込まれている`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のボックスプロット

データフレームからボックスプロットを書く記法に従って、ボックスプロットを書きましょう。
```
boxplot(Sepal.Length~Species, data=iris)
```
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/518682/6772ca66-290c-b652-c76e-19c073eb25a0.png)
簡単に書けました。

でも、もっと高度なプロットを書きたいというユーザーのために、`ggplot2`というパッケージが開発されていますので、使ってみましょう。

## とりあえずパッケージをインストール

パッケージ`ggplot2`、`ggbeeswarm`、`gridExtra`を使うので、それぞれインストールしておいてください。インストールしたら読み込んでおきましょう。
```
library(ggplot2)
library(ggbeeswarm)
library(gridExtra)
```

## ggplotでボックスプロットを書く

```
ggplot(data=iris, aes(x=Species, y=Sepal.Length)) +
 geom_boxplot()
```
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/518682/9fd70d4f-9e78-2fcd-bc19-30cb7bb98034.png)
これでちょっとオシャレなボックスプロットを書けました。`ggplot()`でデータを指定して、`+`に続けて`geom_boxplot()`と書くことでボックスプロットが書けます。

背景を逆にシンプルにしたいという方は、さらに`+`に続けて`theme_classic()`を入れておくと、シンプルな画面になります。
```
ggplot(data=iris, aes(x=Species, y=Sepal.Length)) +
 geom_boxplot() +
 theme_classic()
```
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/518682/2ee2c8c9-4543-3dae-d7d2-23898f289d89.png)
Rのデフォルトの`boxplot`で書いたのとの違いは、ひげの両端にある横棒がないことです。この横棒のことはstaplewexと言います。`ggplot`でも書きたい場合は、エラーバーで代用することができます。
```
ggplot(data=iris, aes(x=Species, y=Sepal.Length)) +
 stat_boxplot(geom="errorbar", width=0.5) +
 geom_boxplot() +
 theme_classic()
```
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/518682/1d6ad860-d5b5-8773-df5d-5c66d17709fe.png)
`stat_boxplot(geom="errorbar")`でstaplewex（のようなもの）を作ることができました。`width`で長さを指定できます。

箱に色を付けたい場合は`fill`を加えます。
```
ggplot(data=iris, aes(x=Species, y=Sepal.Length, fill=Species)) +
 stat_boxplot(geom="errorbar", width=0.5) +
 geom_boxplot() +
 theme_classic()
```
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/518682/df3321c9-fd79-7f36-e6eb-86e1003a6943.png)
凡例が邪魔だなという方は、`theme(legend.position = "none")`を加えます。
```
ggplot(data=iris, aes(x=Species, y=Sepal.Length, fill=Species)) +
 stat_boxplot(geom="errorbar", width=0.5) +
 geom_boxplot() +
 theme_classic() +
 theme(legend.position = "none")
```
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/518682/f38cc3ee-ba19-a3de-665d-0f72332ff8fc.png)
色分けをせず、同じ色で塗りつぶしたい場合は、`geom_boxplot()`の方に`fill`を加えます。
```
ggplot(data=iris, aes(x=Species, y=Sepal.Length)) +
 stat_boxplot(geom="errorbar", width=0.5) +
 geom_boxplot(fill="grey") +
 theme_classic()
```
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/518682/070ef339-2708-571d-ca7d-2ae9c9e48ba9.png)
これで、Rのデフォルトで入っている`boxplot()`と同じような図を作ることができました。

## バイオリンプロットを描く

最近はボックスプロットでも分布の本質がわかりにくいということで、いくつか違う描き方が提案されてます。まずはバイオリンプロットです。
```
ggplot(data=iris, aes(x=Species, y=Sepal.Length)) +
 geom_violin()
```
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/518682/d09487ab-ed30-2d1d-5492-06c620d78f18.png)
ボックスプロットよりも分布が滑らかにイメージできます。背景や色塗りなどの記法は同じです。
```
ggplot(data=iris, aes(x=Species, y=Sepal.Length)) +
 geom_violin(fill="grey") +
 theme_classic()
```
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/518682/308ef47e-c824-9d90-7794-d5fd812c9ed6.png)

# ジッタープロットを描く

すべてのデータ点を表示してしまうというジッタープロットもあります。
```
ggplot(data=iris, aes(x=Species, y=Sepal.Length)) +
 geom_jitter() +
 theme_classic()
```
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/518682/5b913bc3-1a3d-c007-c8d3-f174b54d3335.png)
横方向の点の配置はランダムです。

# スウォームプロットを描く

ジッタープロットよりももっとデータ点を整列させたのがスウォームプロットです。
```
ggplot(data=iris, aes(x=Species, y=Sepal.Length)) +
 geom_beeswarm() +
 theme_classic()
```
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/518682/7db35f5e-4c7d-1de9-749a-fc8d2291f74e.png)
点のサイズや間隔を調整することもできます。
```
ggplot(data=iris, aes(x=Species, y=Sepal.Length)) +
 geom_beeswarm(size=3, cex=2) +
 theme_classic()
```
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/518682/38560297-eb55-372f-fd75-37f493600305.png)
データ点を上手に配置して躍動的に見せることもできます。たとえば`method="smiley"`を加えることで、笑っているような感じになります。
```
ggplot(data=iris, aes(x=Species, y=Sepal.Length)) +
 geom_quasirandom(size=3, method="smiley") +
 theme_classic()
```
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/518682/783cf463-ebb6-b7ba-3e64-38c56a8aca01.png)

# 複数のプロットを重ねる

ggplotの真骨頂は、複数のプロットを簡単に重ねられることです。ここまで描いてきたボックスプロット、バイオリンプロット、スウォームプロットを全部重ねましょう。
```
ggplot(data=iris, aes(x=Species, y=Sepal.Length)) +
 geom_violin() +
 geom_boxplot(fill="grey", width=0.3) +
 geom_beeswarm(size=3, cex=2) +
 theme_classic()
```
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/518682/971fa230-96b4-f352-da71-3fd3270a5b39.png)
それぞれのプロットには一長一短があるので、全部重ねてしまうのも一つの可視化の手段です。

# おまけ：複数のプロットを並べる

`grid.arrange`で複数のプロットを並べて表示できます。論文の図として複数並べるときなどに便利です。
```
p1 <- ggplot(data=iris, aes(x=Species, y=Sepal.Length)) +
      stat_boxplot(geom="errorbar", width=0.5) +
      geom_boxplot(fill="grey") +
      theme_classic()

p2 <- ggplot(data=iris, aes(x=Species, y=Sepal.Length)) +
       geom_violin(fill="grey") +
       theme_classic()

p3 <- ggplot(data=iris, aes(x=Species, y=Sepal.Length)) +
       geom_beeswarm(size=3, cex=2) +
       theme_classic()

p4 <- ggplot(data=iris, aes(x=Species, y=Sepal.Length)) +
       geom_violin() +
       geom_boxplot(fill="grey", width=0.3) +
       geom_beeswarm(size=3, cex=2) +
       theme_classic()

grid.arrange(p1, p2, p3, p4, nrow = 2)
```
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/518682/b2bd01d8-d4a7-2472-7117-bbf9bb8d8071.png)
4種のプロットを、それぞれ`p1`、`p2`、`p3`、`p4`に格納し、これを`grid.arrange`でまとめて表示しました。`nrow`で一行あたりの図の数を指定できます。

（2023年9月26日、了）