超初心者向けのRガイド

g. 各種グラフの雛形

Author

SUGINO Isamu, Build with R4.4.2

Published

December 24, 2024

1 全体の構成

2 Rでの調査データの可視化(Visualization)

 以下では,演習用データの practice.csv ファイルを用いてグラフの描き方を例示する1

csvデータファイルの読み込み
d01 <- read.csv("practice.csv")
d01$SEX  <- factor(d01$sex,
                   levels = 1:2,
                   labels = c("男性", "女性"))

d01$MODE  <- factor(d01$mode,
                    levels = 1:3,
                    labels = c("CAPI", "PAPI", "CASI"))

d01$UNIV  <- factor(d01$edu1,
                    levels = 0:1,
                    labels = c("非四大卒", "四大卒"))

d01$EDU2  <- factor(d01$edu2,
                    levels = 1:3,
                    labels = c("高校卒", "短大卒", "四大卒"))

d01$JOB  <- factor(d01$job,
                   levels = 1:4,
                   labels = c("正規雇用", "非正規雇用", "自営", "無職・学生"))
with(d01, table(q1502, q1501, useNA = "always"))
      q1501
q1502   1  2  3  4  5  6 <NA>
  1     1  0  1  0  0  0    0
  2     0  1  1  1  1  0    0
  3     0 10  5  6  0  0    0
  4     0 39 19  6  2  0    0
  5     2 31 58 12  0  2    0
  6     0 11 47 10  0  0    0
  7     0 18 21 20  3  0    0
  8     1  7 14 11  1  1    0
  9     0  1  1  1  3  0    0
  10    0  0  1  1  4  0    0
  11    0  1  1  0  0  0    0
  <NA>  0  0  1  1  0  0    5
d01$strata5  <- c(1:5)[d01$q1501]
d01$strata10 <- c(10:1)[d01$q1502] # 10が上,1が下を表す様に反転
d01$STRATA5  <- factor(d01$strata5, levels = 1:5,
                       labels = c("上", "中の上", "中の下", "下の上", "下の下"))

with(d01, table(q1700, useNA = "always"))
q1700
   0    1    2    3    4    5    6    7    8    9   10   11 <NA> 
   2    2    4   17   16   65   42   91   81   41   17    1    5 
d01$happy  <- c(0:10)[d01$q1700 + 1]

with(d01, table(q1602, q1604, useNA = "always"))
      q1604
q1602   1  2  3  4  5  6 <NA>
  1     4  5  4  2  7  1    0
  2     4 18 40 14 11  1    0
  3     7 24 63 26 19  0    0
  4     1 16 27 18 14  0    0
  5     1  9 16 12 18  0    0
  <NA>  0  0  0  0  0  0    2
d01$q1604  <- c(1:5)[d01$q1604]
合成得点の作成
with(d01, table(q1801, q1802, useNA = "always"))
      q1802
q1801   1  2  3  4 <NA>
  1    43 53 27 13    0
  2    10 75 63 13    0
  3     2 19 36 11    1
  4     1  1  1  7    0
  <NA>  1  0  4  0    3
cor(d01[, c("q1801", "q1802")], use = "complete")
          q1801     q1802
q1801 1.0000000 0.3582715
q1802 0.3582715 1.0000000
d01$education <- (d01$q1801 + d01$q1802)/2

標準関数は,基本的に with( ) で包んで使用する例で示す。

3 ヒストグラム

3.1 標準関数でのヒストグラム

with(d01,
     hist(fincome)
     )

with(d01,
     hist(fincome,
          main   = "Q29 世帯収入",
          sub    = "(過去1年,税込み,年金・株・副収入等含む)",
          xlab   = "世帯収入(万円)",
          ylab   = "人数",
          family = "serif",      # Macでは "HiraKakuProN-W3"などを指定する。
          col    = "#00640060",  # garkgreenの#006400に透過度60を指定
          las    = 1)
     )

調査票の選択肢の幅の通りに区間を区切る。縦軸は人数ではなくなり密度になるのが問題。
後半は算術平均や中央値の位置を書き込むもので,単なる例。

様々なオプションを付けたhist( )
with(d01,
     hist(fincome,
          breaks = c(0, 50, 100, seq(150, 850, by = 100), 
                     1000, 1250, 1500, 2000, 3000),
          main   = "Q29 世帯収入",
          sub    = "(過去1年,税込み,年金・株・副収入等含む)",
          xlab   = "世帯収入(万円)",
          ylab   = "密度",
          yaxt   = "n", 
          family = "serif",      # Macでは "HiraKakuProN-W3"などを指定する。
          col    = "#556b2f30",  # garkolivegreenに透過度60を指定
          border = "#556b2f",
          las    = 2)
     )

axis(side   = 2,
     at     = c(0, 1), 
     labels = c("0", NA),
     family = "serif",
     las    = 1)

# ここから先は,中央値や算術平均を書き込むためのもので必須ではない。

abline(v = mean(d01$fincome, na.rm = T),
       col = "red",
       lty = "dotted")

axis(side      = 1,
     at        = mean(d01$fincome, na.rm = T), 
     labels    = paste("mean", round(mean(d01$fincome, na.rm = T), 0)), 
     cex.axis  = 0.8,
     col.axis  = "red", 
     family    = "serif",
     las       = 2)

abline(v = median(d01$fincome, na.rm = T),
       col = "blue",
       lty = "dashed")

axis(side      = 1,
     at        = median(d01$fincome, na.rm = T), 
     labels    = paste("median", round(median(d01$fincome, na.rm = T), 0)),
     cex.axis  = 0.8,
     col.axis  = "blue", 
     family    = "serif",
     las       = 2)

3.2 ggplotでのヒストグラム

Rでグラフを描くパッケイジとして絶大な人気を誇るggplot2
base Rとは異なる独特の記法もあって最初はやや敷居が高く感じるが,覚えるにつれ,高品質でかつ高度な統計処理を施したグラフを,さまざまに好みのカスタマイズをして描く事が出来る様になる。
解説書や解説サイトも非常に多い。

基本関数はggplot( )であるが,パッケイジの名前はggplot2なので間違えないように。
installは,そのPC,そのversionのRに対して1回行えばよい(言い換えれば,base Rをupdateしたら追加パッケイジも再度installする事になる)。
library(ggplot2)はRを起動する毎に(ggplotを使用する前に)実行する。そのRセッションを終了するまでは有効。

install.packages("ggplots")   # 最初に1回だけinstallする。
library(ggplot2)              # R session毎に1回必要。

ggplotでは,color = や fill = で指定することで,グループごとのグラフを描く事が出来る。

mean.data <- by(d01$income, d01$SEX, mean, na.rm = T)

annotate( )でそれぞれの算術平均の値を書き込んでいるが,ここは余りうまくないので削除して良い。

ggplot(d01, aes(x     = income, 
                color = SEX,
                fill  = SEX)) +
  geom_histogram(position = "identity",
                 alpha    = .5) +
  geom_text(aes(y     = ..count..,
                label = ifelse(..count.. > 0, ..count.., ""),
                col   = SEX),
            stat  = "bin", 
            vjust = -0.5) +
  geom_vline(xintercept = mean.data,
             color      = c("#F8766D", "#00BFC4"),
             linetype   = "dashed") + 
  labs(title    = "男女別の個人年収",
       subtitle = "東京・千葉・埼玉・神奈川 30-59歳",
       caption  = "2014年3モード比較調査",
       x        = "個人年収(万円)",
       y        = "人数",
       color    = "", 
       fill     = "") +
  theme_minimal() +
  theme(legend.position = c(.8, .7)) +
  annotate("text", 
           x      = mean.data, 
           y      = -4, 
           label  = sprintf("mean %.0f", mean.data),
           color  = c("#F8766D", "#00BFC4"), 
           family = "serif")

4 棒グラフ

4.1 標準関数での棒グラフ

raw dataから棒グラフを描画する際には,変数をそのまま引数に与えてもダメで,集計したものを用いなければならない点に注意。

with(d01, 
     barplot(strata5)
)

(t01 <- with(d01, table(strata5)))
strata5
  1   2   3   4   5 
  4 119 170  69  14 

序に少しオプションを追加する。

with(d01, 
     barplot(t01,
             main   = "5段階階層帰属意識の分布",
             sub    = "東京・千葉・埼玉・神奈川の30-59歳男女(2014年)",
             xlab   = "5段階階層帰属意識",
             names  = c("上", "中の上", "中の下", "下の上", "下の下"),
             ylab   = "人数",
             family = "serif", 
             col    = "#f0808080", 
             border = "#f08080ff", 
             las    = 1)
)

barplot( )の中でtable( )で集計してみる。

with(d01, 
     barplot(table(strata5, SEX), 
             beside = T,
             legend.text = c("上", "中の上", "中の下",
                             "下の上", "下の下"),
             main   = "5段階階層帰属意識の分布",
             sub    = "東京・千葉・埼玉・神奈川の30-59歳男女(2014年)",
             xlab   = "5段階階層帰属意識",
             ylab   = "人数",
             family = "serif", 
             col    = heat.colors(5), 
             border = heat.colors(5), 
             las    = 1)
)

barplot( )の中でprop.table(table( ), margin = 2)で集計してみる。

with(d01, 
     barplot(prop.table(table(strata5, SEX), margin = 2), 
             beside = T,
             legend.text = c("上", "中の上", "中の下", 
                             "下の上", "下の下"),
             main   = "5段階階層帰属意識の分布",
             sub    = "東京・千葉・埼玉・神奈川の30-59歳男女(2014年)",
             xlab   = "5段階階層帰属意識",
             ylab   = "割合",
             family = "serif", 
             col    = topo.colors(5), 
             border = topo.colors(5), 
             las    = 1)
)

いわゆる帯グラフ。割合を%にしてみた。
必要度は低いのだが,凡例legendに色々とオプションを付けて例示している。

with(d01, 
     barplot(prop.table(table(strata5, SEX), margin = 2)*100, 
             beside = F,
             legend.text = c("上", "中の上", "中の下", 
                             "下の上", "下の下"),
             args.legend = list(x       = 2.0, 
                                y       = 75,
                                xjust   = 0,
                                box.col = NA, 
                                cex     = 0.9,
                                bg      = "#f5f5dc80",
                                horiz   = F,
                                border  = NA),
             main   = "5段階階層帰属意識の分布",
             sub    = "東京・千葉・埼玉・神奈川の30-59歳男女(2014年)",
             xlab   = "5段階階層帰属意識",
             ylab   = "パーセント",
             family = "serif", 
             col    = terrain.colors(5), 
             border = "grey20", 
             las    = 1)
)

4.2 ggplotでの棒グラフ

geom_barでは集計表を渡す必要は無い。
x軸からNAを除外するのに手間がかかる2
度数を付記する為に geom_text を使う。

ggplot(d01, aes(x = STRATA5)) +
  geom_bar(fill = "#0000cd60") +
  geom_text(aes(y     = ..count..,
                label = ifelse(..count.. > 0, ..count.., "")),
            stat  = "count", 
            vjust = -0.2) +
  scale_x_discrete(na.translate = F) +
  labs(title    = "階層帰属意識の分布",
       subtitle = "30-59歳男女",
       caption  = "東京・千葉・埼玉・神奈川(2014年)",
       x        = "5段階階層帰属意識",
       y        = "人数") +
  theme_light()

xにSEXを置いてfillにSTRATA5を指定する事で,男女の中での内訳として階層帰属意識を表示する。
position = “fill”としてy軸を上まで引き延ばして帯グラフとする。
NAの除外がなお一層面倒なので,データフレイムの指定を工夫してNAを除外している3

ggplot(d01[!is.na(d01$STRATA5),], 
       aes(x = SEX, color = STRATA5, fill = STRATA5)) +
  geom_bar(position = "fill", alpha = .2) +
  geom_text(aes(label = ifelse(..count.. > 0, ..count.., "")),
            stat  = "count", 
            position = position_fill(vjust = 0.5)) +
  scale_color_manual(values = c("brown", "darkgreen", "forestgreen",
                                "mediumblue", "lightskyblue")) +
  scale_fill_manual(values = c("brown", "darkgreen", "forestgreen",
                               "mediumblue", "lightskyblue")) +
  labs(title    = "階層帰属意識の分布",
       subtitle = "30-59歳男女",
       caption  = "東京・千葉・埼玉・神奈川(2014年)",
       x        = "",
       y        = "割合",
       color    = "階層帰属意識",
       fill     = "階層帰属意識") +
  theme_light()

更にfacet_grid( )でMODE別に表示する。

ggplot(d01[!is.na(d01$STRATA5),], 
       aes(x = SEX, color = STRATA5, fill = STRATA5)) +
  geom_bar(position = "fill", alpha = .2) +
  geom_text(aes(label = ifelse(..count.. > 0, ..count.., "")),
            stat  = "count", 
            position = position_fill(vjust = 0.5)) +
  scale_fill_manual(values = c("brown", "darkgreen", "forestgreen",
                                "mediumblue", "lightskyblue"),
                    na.translate = F) +
  scale_color_manual(values = c("brown", "darkgreen", "forestgreen",
                                "mediumblue", "lightskyblue"),
                    na.translate = F) +
  labs(title    = "階層帰属意識の分布",
       subtitle = "30-59歳男女",
       caption  = "東京・千葉・埼玉・神奈川(2014年)",
       x        = "",
       y        = "割合",
       color    = "階層帰属意識",
       fill     = "階層帰属意識") +
  theme_light() +
  facet_grid(~ MODE)

5 散布図

5.1 標準関数での散布図

with(d01, 
     plot(strata10, happy)
)

with(d01, 
     plot(strata10, happy,
          bty  = "n", 
          las  = 1,
          main = "階層帰属意識と幸福感",
          sub  = "",
          xlab = "10段階階層帰属意識(1 下← →上 10)",
          ylab = "幸福感(0 不幸← →幸福10)",
          family = "serif",
          pch  = "●",
          col  = "#7CAE0050")
)

マーカーを塗り潰しにした上でcolorに透過度を指定して,度数が多いところ程濃くなる様に工夫している。

with(d01, 
     plot(strata10, happy,
          bty  = "n", 
          las  = 1,
          main = "階層帰属意識と幸福感",
          sub  = sprintf("(平均:階層帰属意識 %.1f,幸福度 %.1f)", 
                         mean(d01$strata10, na.rm = T),
                         mean(d01$happy,    na.rm = T)),
          xlab = "10段階階層帰属意識(1 下← →上 10)",
          ylab = "幸福感(0 不幸← →幸福10)",
          family = "serif",
          pch  = "●",
          col  = "#7CAE0050")
)

abline(lm(happy ~ strata10, d01), 
       lty = "dotted",
       lwd = 3,
       col = "#F8766Ddd")

text(mean(d01$strata10, na.rm = T), 
     mean(d01$happy,    na.rm = T),
     "×", 
     col = "blue",
     cex = 1.5,  # textのsize
     font = 2)   # bold指定

5.2 ggplotでの散布図

ggplot(d01, aes(x = strata10, y = happy)) +
  geom_point()

回帰直線は,geom_abline( )で書き込むよりも,geom_smooth(method = “lm”)で書き込む方が楽。defaultでは95%信頼区間を描くが,不要であれば se = F とすれば良い。

ggplot(d01, aes(x = strata10, y = happy)) +
  geom_point(alpha = .4,
             color = "#7CAE00") +
  scale_x_continuous(breaks = 1:10) +
  scale_y_continuous(breaks = 0:10) +
  labs(title    = "階層帰属意識の分布と幸福度",
       subtitle = sprintf("(平均:階層帰属意識 %.1f,幸福度 %.1f)", 
                          mean(d01$strata10, na.rm = T),
                          mean(d01$happy,    na.rm = T)),
       caption  = "東京・千葉・埼玉・神奈川 30-59歳男女(2014年)",
       x        = "10段階階層帰属意識(1 下← →上 10)",
       y        = "幸福感(0 不幸← →幸福10)",
       tag      = "図1") +
  theme_classic() +
  geom_smooth(method = "lm", se = F, linetype = "dotted")

但しこれだと,標準関数ではなくggplotを使用しているメリットは余り無い。

標準関数では簡単に出来ない事をやってみる。
前の例とのスクリプトの違いは非常に僅かである。

ggplot(d01, aes(x = strata10, y = happy, color = SEX)) +
  geom_point(alpha = .4) +
  scale_x_continuous(breaks = 1:10) +
  scale_y_continuous(breaks = 0:10) +
  labs(title    = "階層帰属意識の分布と幸福度",
       subtitle = sprintf("(平均:階層帰属意識 %.1f,幸福度 %.1f)", 
                          mean(d01$strata10, na.rm = T),
                          mean(d01$happy,    na.rm = T)),
       caption  = "東京・千葉・埼玉・神奈川 30-59歳男女(2014年)",
       x        = "10段階階層帰属意識(1 下← →上 10)",
       y        = "幸福感(0 不幸← →幸福10)",
       color    = "",
       tag      = "図1") +
  theme_classic() +
  geom_smooth(method = "lm", se = F, linetype = "dotted") +
  theme(legend.position = c(.9, .2))

ggplot(d01[!is.na(d01$UNIV), ],
       aes(x = strata10, y = happy, 
                color = SEX, fill = SEX)) +
  geom_jitter(alpha = .4) +
  scale_x_continuous(breaks = 1:10) +
  scale_y_continuous(breaks = 0:10) +
  labs(title    = "階層帰属意識の分布と幸福度",
       subtitle = sprintf("(平均:階層帰属意識 %.1f,幸福度 %.1f)", 
                          mean(d01$strata10, na.rm = T),
                          mean(d01$happy,    na.rm = T)),
       caption  = "東京・千葉・埼玉・神奈川 30-59歳男女(2014年)",
       x        = "10段階階層帰属意識(1 下← →上 10)",
       y        = "幸福感(0 不幸← →幸福10)",
       color    = "",
       fill     = "",
       tag      = "図1") +
  theme_minimal() +
  geom_smooth(method = "loess", se = T, linetype = "dashed") +
  geom_hline(yintercept = mean(d01$happy, na.rm = T),
             linetype   = "dashed",
             color      = "#7CAE00") +
  facet_wrap( ~ UNIV) +
  theme(legend.position = c(.5, .2))

6 箱ひげ図

6.1 標準関数での箱ひげ図

1変数の箱ひげ図では余り利点が活かされない。

with(d01,
     boxplot(happy)
     )

グループ間比較には有効。
序に幾つかオプションを付けている。
family や bty はboxplot( )では其の儘指定しても効かないので,par( )に入れて指定する。

with(d01,
     boxplot(happy ~ JOB,
             varwidth = T,
             main     = "幸福感の職業間比較",
             sub      = "東京・千葉・埼玉・神奈川 30-59歳男女(2014年)",
             xlab     = "従業上の地位",
             ylab     = "幸福感(0 不幸← →幸福10)",
             col      = c("#99003360", "#99CC0060",
                          "#9999FF60", "#6699FF60"),
             border   = c("#990033", "#99CC00", 
                          "#9999FF", "#6699FF"),
             las      = 1,
             par(family = "serif", bty = "n")
             )
     )

6.2 ggplotでの箱ひげ図

敢えて多くのオプションを付けて例示としている。

ggplot(d01[!is.na(d01$JOB), ],
       aes(x = JOB, y = strata10, color = JOB, fill = JOB)) +
  geom_boxplot(varwidth = T, alpha = .3) +
  scale_y_continuous(breaks = 1:10) + 
  labs(title    = "階層帰属意識の箱ひげ図",
       caption  = "東京・千葉・埼玉・神奈川 30-59歳男女(2014年)",
       x        = "従業上の地位",
       y        = "階層帰属意識(下← →上)",
       color    = "",
       fill     = "",
       tag      = "図A") + 
  theme_minimal() +
  theme(legend.position = "none")

ggplot(d01[!is.na(d01$JOB), ],
       aes(x = JOB, y = strata10, color = JOB, fill = JOB)) +
  geom_boxplot(varwidth = T, alpha = .3) +
  scale_y_continuous(breaks = 1:10) + 
  stat_summary(fun.y = "mean", geom = "point", color = "red") +
  labs(title    = "階層帰属意識の箱ひげ図",
       caption  = "東京・千葉・埼玉・神奈川 30-59歳男女(2014年)",
       x        = "従業上の地位",
       y        = "階層帰属意識(下← →上)",
       color    = "",
       fill     = "",
       tag      = "図A") + 
  theme_minimal() +
  theme(legend.position = "none") +
  facet_wrap(~ SEX)

ggplot(d01[!is.na(d01$JOB) & !is.na(d01$UNIV), ],
       aes(x = JOB, y = strata10, color = JOB, fill = JOB)) +
  geom_boxplot(varwidth = T, alpha = .3) +
  geom_jitter(width = .2, height = .05, alpha = .2) +
  scale_y_continuous(breaks = 1:10) + 
  stat_summary(fun.y = "mean", geom = "point", color = "red") +
  labs(title    = "階層帰属意識の箱ひげ図",
       caption  = "東京・千葉・埼玉・神奈川 30-59歳男女(2014年)",
       x        = "従業上の地位",
       y        = "階層帰属意識(下← →上)",
       color    = "",
       fill     = "",
       tag      = "図A") + 
  theme_minimal() +
  theme(legend.position = "none") +
  facet_grid(SEX ~ UNIV)

6.3 ggplotでのヴァイオリン・プロット

ggplot(d01[!is.na(d01$JOB), ],
       aes(x = JOB, y = strata10, color = JOB, fill = JOB)) +
  geom_boxplot(width = .2, alpha = .3) +
  geom_violin(alpha = 0) +
  stat_summary(fun.y = "mean", geom = "point", color = "red") +
  scale_y_continuous(breaks = 1:10) + 
  labs(title    = "階層帰属意識の箱ひげ図とヴァイオリン図",
       caption  = "東京・千葉・埼玉・神奈川 30-59歳男女(2014年)",
       x        = "従業上の地位",
       y        = "階層帰属意識(下← →上)",
       color    = "",
       fill     = "",
       tag      = "図A") + 
  theme_minimal() +
  theme(legend.position = "none") +
  facet_grid(~SEX)

7 モザイクプロット

7.1 標準関数でのモザイクプロット

分割表を其の儘可視化する。
基本的なオプションを付けて示す。
x軸ラベルは冗長なので情報表示に活用している。

addmargins(tab01 <- with(d01, table(SEX, EDU2)))
      EDU2
SEX    高校卒 短大卒 四大卒 Sum
  男性     56     31     74 161
  女性     72     92     51 215
  Sum     128    123    125 376
(chi01 <- chisq.test(tab01))

    Pearson's Chi-squared test

data:  tab01
X-squared = 29.334, df = 2, p-value = 4.268e-07
V <- sqrt(chi01$statistic/(min(dim(tab01) - 1) * sum(tab01)))
names(V) <- "Cramer's V"
V
Cramer's V 
 0.2793122 
with(d01,
     mosaicplot(SEX ~ EDU2,
                off = 3,
                col = c("#99003360", "#99CC0060", "#9999FF60"),
                border = "#777777",
                main     = "男女別の最終学歴",
                sub      = "東京・千葉・埼玉・神奈川 30-59歳男女(2014年)",
                xlab     = sprintf("χ2(%d)= %.1f, Cramer's V= %.3f", 
                                   chi01$parameter, 
                                   chi01$statistic, V),
                ylab     = "最終学歴",
                las      = 1,
                par(family = "serif")
                )
     )

7.2 ggmosaicでのモザイクプロット

ggplotでモザイクプロットを描くには更に追加のパッケイジをインストールする必要があるので必ずしも推奨しない。

# install.packages("ggmosaic")
library(ggmosaic)
addmargins(tab02 <- with(d01, table(JOB, EDU2, SEX)))
, , SEX = 男性

            EDU2
JOB          高校卒 短大卒 四大卒 Sum
  正規雇用       37     25     64 126
  非正規雇用      6      1      2   9
  自営           10      4      4  18
  無職・学生      3      1      3   7
  Sum            56     31     73 160

, , SEX = 女性

            EDU2
JOB          高校卒 短大卒 四大卒 Sum
  正規雇用       12     22     20  54
  非正規雇用     31     36     15  82
  自営            7     10      2  19
  無職・学生     22     24     14  60
  Sum            72     92     51 215

, , SEX = Sum

            EDU2
JOB          高校卒 短大卒 四大卒 Sum
  正規雇用       49     47     84 180
  非正規雇用     37     37     17  91
  自営           17     14      6  37
  無職・学生     25     25     17  67
  Sum           128    123    124 375
ggplot(d01[complete.cases(d01$JOB, d01$EDU2), ]) +
  geom_mosaic(aes(x = product(JOB, EDU2), fill = JOB), na.rm = T) +
  labs(title = '性別・学歴別の従業上の地位',
    subtitle = , 
     caption = "東京・千葉・埼玉・神奈川 30-59歳男女(2014年)",
       x     = "",
       y     = "") +
  theme_mosaic() + 
  theme(legend.position = "none",
        text = element_text(family = "serif")) +
  facet_wrap(~ SEX, scale = "free")

8 交互作用プロット

8.1 標準関数での交互作用プロット

X軸はカテゴリカルに扱われており,厳密にはやや問題がある。
x軸は等間隔尺度か,単なる順序尺度の方が適しているか。

with(d01,
     interaction.plot(edu, SEX, income,
                      fun    = function(x) mean(x, na.rm = T), 
                      ylim   = c(0,800),
                      bty    = "l", 
                      lty    = c("dotted", "solid"), 
                      main   = "性・教育年数別の世帯年収平均",
                      sub    = "※ x軸のメモリが等間隔で正しくない",
                      xlab   = "本人教育年数(年)",
                      ylab   = "平均世帯年収(万円)", 
                 trace.label = "性別",
                      las    = 1,
                      col    = c("#008b8b", "#663333"),
                      family = "serif",
                      fixed  = T
                      )
)

8.2 ggplotでの交互作用プロット

x-yグラフがzによって2本になっているのが交互作用プロットである。
つまり3変数の関連をグラフにしたものであり,或意味では実はggplotでの交互作用の例は既に上に出てきている。
ここでは標準関数と同様で,より正確なグラフをggplotで描画する。

ggplot(d01,
       aes(x = edu, y = income, color = SEX)) +
  stat_summary(fun = "mean", geom = "line") +
  labs(title    = "教育年数と本人収入(男女別)",
       caption  = "東京・千葉・埼玉・神奈川 30-59歳男女(2014年)",
       x        = "教育年数(年)",
       y        = "個人年収平均(万円)",
       color    = "",
       fill     = "",
       tag      = "Fig. 1") + 
  theme_minimal() +
  theme(legend.position = c(.9, .2))

これを別のグラフで書くと以下の様にもなる。

gg01 <- 
ggplot(d01,
       aes(x = edu, y = income, color = SEX, fill = SEX)) +
  geom_jitter(width = .1, height = .05, alpha = .4) +
  geom_smooth(method = "loess") + 
  labs(title    = "教育年数と本人収入(男女別)",
       subtitle = "東京・千葉・埼玉・神奈川 30-59歳男女(2014年)",
       caption  = "",
       x        = "教育年数(年)",
       y        = "個人年収(万円)",
       color    = "",
       fill     = "",
       tag      = "Fig. 1") + 
  theme_minimal() +
  theme(legend.position = c(.2, .8))
gg01
gg01 + coord_cartesian(ylim = c(0, 1000)) +
  labs(caption = "縦軸は2500まで存在するが描画範囲を1000までに限定した。",
       tag     = "Fig. 2")

Footnotes

  1. データと説明書PDFは『入門・社会統計学』旧版サポートウェブのフロントページで提供している。↩︎

  2. na.translate = F↩︎

  3. !is.na(d01$STRATA5)の行(ケース)だけに限定している。↩︎