install.packages("pacman") # 最初の1回だけ実行1 第1回 売上をまとめた表をつくる
1.1 はじめに
第1回の内容は,POSデータを集約して,売上金額や売上個数の合計を計算し,販売状況の特徴を把握しやすい図や表を作成することです。
1.2 この章で使うファイルとパッケージ
ここで用いるデータが記録されているファイルは,Microsoft社のExcelのファイルです。 最近のMS Excelで作成されたファイルは拡張子に.xlsxがついています。 第1回の内容で扱うファイルは、
拡張子(extension)は,ファイル名の最後についている.xlsxや.csvなどの文字列のことで,ファイルの種類を示しています。Windowsではデフォルトで拡張子が表示されない設定になっているかもしれないので,必ず拡張子を表示させる設定にしておいてください。.exeファイルを知らずに実行すると,ウイルスに感染する可能性があるので,拡張子を表示させることはセキュリティ上も重要です。
chp1.xlsx
という名前のファイルです。 このファイルは,Rの作業ディレクトリ(working directory)の中にあるdataフォルダに保存しておきます。
Rの機能を拡張するために,ここでは以下のパッケージを用います。
-
tidyverse: データの読み込み,加工,可視化に使うパッケージ -
readxl: Excelファイルを読み込むためのパッケージ
通常,Rではinstall.packages()関数を使ってパッケージをインストールし,library()で読み出しますが,ここではpacmanパッケージを使って一括でインストール・読み込みを行います。
pacmanパッケージを使うために,以下のコードを実行してください。
pacmanパッケージには便利な関数がいろいろありますが,ここではp_load()関数を使って複数のパッケージを一括で読み込みます。まだインストールされていないパッケージがあれば,自動でインストールされます。 便利なパッケージをいろいろ読み込んでおきましょう。
pacman::p_load(tidyverse, readxl, ggthemes, gt, gtExtras)-
ggtheme: グラフのテーマを変更するためのパッケージ -
gt: 表を作成するためのパッケージ -
gtExtras:gtパッケージの拡張機能を提供するパッケージ
pacman::p_load()のように,「パッケージ名::関数名」という書き方で,パッケージ名を指定して関数を使うと,p_load()関数がpacmanパッケージの関数であることが分かりやすいので,似たような名前の関数があるときは,パッケージ名をつけて使うといいでしょう。 たとえば,dplyr::select()関数やreadxl::read_excel()関数です。
うえでも説明したとおり、今後分析に使う予定のファイルはすべて作業ディレクトリのdataフォルダにいれてある、と想定したソースコードを作成しているので、もしdataフォルダではない場所にファイルを保存している場合は、data/の部分を適宜変更してください。
Rは作業ディレクトリとなっているフォルダを軸にしてファイルを読み込むため,ファイルの場所に注意してください。 ここでは作業ディレクトリの中にdataフォルダを作り,そこにchp1.xlsxを保存してあるので,data/chp1.xlsxと指定することでファイルにアクセスしています。
1.3 Rの準備
- Rをインストールしておきましょう。
- RStudioかVS Codeをインストールしておきましょう。
- Rのパッケージ
tidyverseをインストールしておきましょう。 - 作業ディレクトリを設定しておきましょう。
これらの内容が分からない場合は,R入門の資料や本を参照してください。
1.4 データの読み込み
まずはreadxlパッケージを使ってデータchp1.xlsxを読み込んでみましょう。 このExcelファイルのシートの一覧を表示してみます。
readxl::excel_sheets("data/chp1.xlsx")[1] "いつものPOSデータ" "ピボットテーブル" "表1-2・図1-19"
[4] "表1-4・図1-28・図1-29" "表1-5・図1-32" "表1-6"
[7] "図1-38"
excel_sheets()関数はデフォルトで1番目のシートを読み込みます。 「いつものPOSデータ」を読み込みたいので,特に指定せずにread_excel()関数を使って読み込みます。
df <- readxl::read_excel("data/chp1.xlsx")
head(df) # 戦闘6行を表示Warning in attr(x, "align"): 'xfun::attr()' は廃止予定です
'xfun::attr2()' を代わりに使って下さい
help("Deprecated") を見て下さい
| レシート番号 | 日付 | 曜日 | 時間 | 性別 | 年代 | メーカー | 商品名 | 単価 | 個数 | 金額 |
|---|---|---|---|---|---|---|---|---|---|---|
| R000001 | 2023-01-02 | 月 | 10 | 女性 | 30代 | 競合A | おいしい緑茶 | 160 | 2 | 320 |
| R000001 | 2023-01-02 | 月 | 10 | 女性 | 30代 | 競合B | 静岡の緑茶 | 170 | 2 | 340 |
| R000002 | 2023-01-02 | 月 | 10 | 男性 | 60歳以上 | 競合A | おいしい濃茶 | 160 | 2 | 320 |
| R000002 | 2023-01-02 | 月 | 10 | 男性 | 60歳以上 | 競合B | 静岡の緑茶 | 170 | 4 | 680 |
| R000003 | 2023-01-02 | 月 | 10 | 男性 | 50代 | 競合C | ほうじ茶 | 140 | 1 | 140 |
| R000004 | 2023-01-02 | 月 | 10 | 女性 | 50代 | 競合D | ウーロン茶 | 140 | 3 | 420 |
どんな変数があるのか確認するにはnames()関数を使います。
names(df) [1] "レシート番号" "日付" "曜日" "時間" "性別"
[6] "年代" "メーカー" "商品名" "単価" "個数"
[11] "金額"
1.5 データの属性を確認する。
データの属性や型を確認するにはstr()関数を使います。
str(df)tibble [374,090 × 11] (S3: tbl_df/tbl/data.frame)
$ レシート番号: chr [1:374090] "R000001" "R000001" "R000002" "R000002" ...
$ 日付 : POSIXct[1:374090], format: "2023-01-02" "2023-01-02" ...
$ 曜日 : chr [1:374090] "月" "月" "月" "月" ...
$ 時間 : num [1:374090] 10 10 10 10 10 10 10 10 10 10 ...
$ 性別 : chr [1:374090] "女性" "女性" "男性" "男性" ...
$ 年代 : chr [1:374090] "30代" "30代" "60歳以上" "60歳以上" ...
$ メーカー : chr [1:374090] "競合A" "競合B" "競合A" "競合B" ...
$ 商品名 : chr [1:374090] "おいしい緑茶" "静岡の緑茶" "おいしい濃茶" "静岡の緑茶" ...
$ 単価 : num [1:374090] 160 170 160 170 140 140 160 150 150 160 ...
$ 個数 : num [1:374090] 2 2 2 4 1 3 1 2 3 4 ...
$ 金額 : num [1:374090] 320 340 320 680 140 420 160 300 450 640 ...
dplyr::glimpse()関数を使うと,データの概要をより見やすく表示できます。
dplyr::glimpse(df)Rows: 374,090
Columns: 11
$ レシート番号 <chr> "R000001", "R000001", "R000002", "R000002", "R000003", "R…
$ 日付 <dttm> 2023-01-02, 2023-01-02, 2023-01-02, 2023-01-02, 2023-01-…
$ 曜日 <chr> "月", "月", "月", "月", "月", "月", "月", "月", "月", "月", "月", "月…
$ 時間 <dbl> 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 1…
$ 性別 <chr> "女性", "女性", "男性", "男性", "男性", "女性", "女性", "女性", "女性", "男性…
$ 年代 <chr> "30代", "30代", "60歳以上", "60歳以上", "50代", "50代", "50代", "50代…
$ メーカー <chr> "競合A", "競合B", "競合A", "競合B", "競合C", "競合D", "競合A", "自社", "自…
$ 商品名 <chr> "おいしい緑茶", "静岡の緑茶", "おいしい濃茶", "静岡の緑茶", "ほうじ茶", "ウーロン茶", "お…
$ 単価 <dbl> 160, 170, 160, 170, 140, 140, 160, 150, 150, 160, 160, 17…
$ 個数 <dbl> 2, 2, 2, 4, 1, 3, 1, 2, 3, 4, 1, 2, 2, 1, 1, 2, 1, 2, 3, …
$ 金額 <dbl> 320, 340, 320, 680, 140, 420, 160, 300, 450, 640, 160, 34…
この表の上部をみると、このデータには変数が11個,観測値が374,090個あることが分かります。 また,変数名の横に<chr>や<dbl>といった文字が表示されていますが,これは変数の型を示しています。 <chr>は文字列型,<dbl>は数値型,<dttm>は日付型を示しています。
文字型,数値型,日付型以外にも,
-
<fct>: 因子型 -
<int>: 整数型 -
<lgl>: 論理型
などがあります。
1.6 データの概要を確認する
データの属性を確認するために,summary()関数を使ってみましょう。 基本関数summary()は,データの記述統計量などを返してくれる関数です。
summary(df) レシート番号 日付 曜日
Length:374090 Min. :2023-01-02 00:00:00.00 Length:374090
Class :character 1st Qu.:2023-05-09 00:00:00.00 Class :character
Mode :character Median :2023-07-28 00:00:00.00 Mode :character
Mean :2023-07-16 10:09:45.75
3rd Qu.:2023-09-23 00:00:00.00
Max. :2023-12-31 00:00:00.00
時間 性別 年代 メーカー
Min. :10.00 Length:374090 Length:374090 Length:374090
1st Qu.:13.00 Class :character Class :character Class :character
Median :16.00 Mode :character Mode :character Mode :character
Mean :15.57
3rd Qu.:18.00
Max. :21.00
商品名 単価 個数 金額
Length:374090 Min. :140.0 Min. : 1.000 Min. : 140.0
Class :character 1st Qu.:150.0 1st Qu.: 1.000 1st Qu.: 160.0
Mode :character Median :160.0 Median : 2.000 Median : 280.0
Mean :154.5 Mean : 1.783 Mean : 275.7
3rd Qu.:160.0 3rd Qu.: 2.000 3rd Qu.: 320.0
Max. :170.0 Max. :14.000 Max. :2100.0
この表より,
- 日付は2023年1月2日から2023年12月31日まで
- 時間は10:00から21:00まで
- 単価は数値で,140〜170
- 個数は数値で,1〜14
- 金額は数値で,140〜2100
となっていることがわかります。 また文字型となっている曜日,性別,年代,メーカー,商品名はデータの個数としてLength:が出力されていることがわかります。 文字列のsummary()を出力しても意味がないので,文字型の変数を除外して,数値型の変数だけを表示するには,select()関数とwhere()関数を使い, is.double関数を使って数値型の変数だけを選択します。
df |>
select(where(is.double)) |>
summary() 日付 時間 単価
Min. :2023-01-02 00:00:00.00 Min. :10.00 Min. :140.0
1st Qu.:2023-05-09 00:00:00.00 1st Qu.:13.00 1st Qu.:150.0
Median :2023-07-28 00:00:00.00 Median :16.00 Median :160.0
Mean :2023-07-16 10:09:45.75 Mean :15.57 Mean :154.5
3rd Qu.:2023-09-23 00:00:00.00 3rd Qu.:18.00 3rd Qu.:160.0
Max. :2023-12-31 00:00:00.00 Max. :21.00 Max. :170.0
個数 金額
Min. : 1.000 Min. : 140.0
1st Qu.: 1.000 1st Qu.: 160.0
Median : 2.000 Median : 280.0
Mean : 1.783 Mean : 275.7
3rd Qu.: 2.000 3rd Qu.: 320.0
Max. :14.000 Max. :2100.0
is.double()関数は,引数の型が数値型かどうかを判定する関数で,数値型の場合はTRUEを返し,そうでない場合はFALSEを返します。このように,is.型名()関数は,型を判定する関数として使われます。 条件を満たす変数だけを選択するdplyr::select()関数と,dplyr::where()関数を使うことで変数の型を指定して変数を抽出できます。
1.7 因子型
これらの文字型変数曜日,性別,年代,メーカー,商品名は,どのカテゴリーに属しているかを表しているカテゴリカルデータであるため, 文字型から因子型(factor)に変換しておきましょう。 変数を因子型に変更するには,facor()関数やas.factor()関数を使います。 ここでは,曜日に順番があるため,levelsオプションとorderedオプションで曜日の種類と順番を指定しています。
変数の型を変更したので,もう一度,summary()関数を使ってデータを確認してみましょう。
summary(df) レシート番号 日付 曜日 時間
Length:374090 Min. :2023-01-02 00:00:00.00 月:36468 Min. :10.00
Class :character 1st Qu.:2023-05-09 00:00:00.00 火:44573 1st Qu.:13.00
Mode :character Median :2023-07-28 00:00:00.00 水:52418 Median :16.00
Mean :2023-07-16 10:09:45.75 木:37703 Mean :15.57
3rd Qu.:2023-09-23 00:00:00.00 金:66894 3rd Qu.:18.00
Max. :2023-12-31 00:00:00.00 土:74754 Max. :21.00
日:61280
性別 年代 メーカー 商品名
女性:274659 20歳未満:19102 競合A:144742 ウーロン茶 :31905
男性: 99431 20代 :49716 競合B: 46516 おいしい濃茶:59910
30代 :81065 競合C: 39190 おいしい緑茶:84832
40代 :74773 競合D: 31905 ほうじ茶 :39190
50代 :93194 自社 :111737 静岡の緑茶 :46516
60歳以上:56240 濃い茶 :45982
緑茶 :65755
単価 個数 金額
Min. :140.0 Min. : 1.000 Min. : 140.0
1st Qu.:150.0 1st Qu.: 1.000 1st Qu.: 160.0
Median :160.0 Median : 2.000 Median : 280.0
Mean :154.5 Mean : 1.783 Mean : 275.7
3rd Qu.:160.0 3rd Qu.: 2.000 3rd Qu.: 320.0
Max. :170.0 Max. :14.000 Max. :2100.0
すると,曜日,性別,年代,メーカー,商品名がカテゴリー変数として認識され,カテゴリーごとの個数が表示されています。
1.8 条件によるデータの抽出
メーカー変数が自社の場合だけを抽出するには,dplyr::filter()関数を使います。 filter()関数は,引数にメーカー == "自社という条件を指定することで,条件に合致するデータだけを抽出します。
Warning in attr(x, "align"): 'xfun::attr()' は廃止予定です
'xfun::attr2()' を代わりに使って下さい
help("Deprecated") を見て下さい
| レシート番号 | 日付 | 曜日 | 時間 | 性別 | 年代 | メーカー | 商品名 | 単価 | 個数 | 金額 |
|---|---|---|---|---|---|---|---|---|---|---|
| R000005 | 2023-01-02 | 月 | 10 | 女性 | 50代 | 自社 | 濃い茶 | 150 | 2 | 300 |
| R000005 | 2023-01-02 | 月 | 10 | 女性 | 50代 | 自社 | 緑茶 | 150 | 3 | 450 |
| R000010 | 2023-01-02 | 月 | 10 | 女性 | 50代 | 自社 | 濃い茶 | 150 | 2 | 300 |
| R000010 | 2023-01-02 | 月 | 10 | 女性 | 50代 | 自社 | 緑茶 | 150 | 1 | 150 |
| R000011 | 2023-01-02 | 月 | 10 | 男性 | 20代 | 自社 | 緑茶 | 150 | 1 | 150 |
| R000012 | 2023-01-02 | 月 | 10 | 女性 | 20代 | 自社 | 緑茶 | 150 | 1 | 150 |
1.9 基礎集計でデータの傾向をチェック
メーカーごとの売上金額合計を示す表を作成してみましょう。 Excelでピボットテーブルを使う手続が教科書で解説されていますが,Rだとdplyrパッケージを使って簡単にできます。
Warning in attr(x, "align"): 'xfun::attr()' は廃止予定です
'xfun::attr2()' を代わりに使って下さい
help("Deprecated") を見て下さい
| メーカー | 売上金額合計 |
|---|---|
| 競合A | 42695520 |
| 競合B | 13537440 |
| 競合C | 9289700 |
| 競合D | 7486080 |
| 自社 | 30126150 |
これだけです。 キレイな表にするなら,gt()関数とgtExtraパッケージを使うといいでしょう。
df_maker_sales |>
gt() |>
fmt_number(columns = 2:2, decimals = 0) |>
tab_header(title = "表1-2 メーカーごとの売上金額") |>
gt_theme_pff() |> # テーマを適用
as_raw_html()| 表1-2 メーカーごとの売上金額 | |
|---|---|
| メーカー | 売上金額合計 |
次に,各メーカーのどの商品が,平均何円で売られているのか,を調べてみましょう。 group_by()関数の引数に,メーカーと商品名を指定して,summarise()関数でグループごとの平均単価を計算し, arrange()関数でメーカーと平均単価でソートします。desc()関数は降順にソートするための関数です。
df_maker_item <- df |>
group_by(メーカー, 商品名) |> # メーカーと商品名でグループ化
summarise(平均単価 = mean(単価)) |> # 平均単価を計算
arrange(メーカー, desc(平均単価)) |># メーカーと平均単価でソート
ungroup()`summarise()` has grouped output by 'メーカー'. You can override using the
`.groups` argument.
df_maker_item |>
gt() |>
fmt_number(columns = 3:3, decimals = 0) |>
tab_header(title = "表1−3 商品ごとの単価") |>
gt_theme_pff() |> # テーマを適用
as_raw_html()| 表1−3 商品ごとの単価 | ||
|---|---|---|
| メーカー | 商品名 | 平均単価 |
1.10 資料作成に必要なデータを取り出す
データ全体における売上金額と売上個数を計算して,各月と各時間帯にの売上金額を計算してみる。
Warning in attr(x, "align"): 'xfun::attr()' は廃止予定です
'xfun::attr2()' を代わりに使って下さい
help("Deprecated") を見て下さい
| 売上金額合計 | 売上個数合計 |
|---|---|
| 103134890 | 667147 |
自社製品ごとの個数と金額を計算してみましょう。
df_jisha_total <- df |>
filter(メーカー == "自社") |> # 自社製品だけを抽出
group_by(商品名) |>
summarise(
売上金額合計 = sum(金額),
売上個数合計 = sum(個数)
) |>
arrange(desc(売上金額合計))
df_jisha_totalWarning in attr(x, "align"): 'xfun::attr()' は廃止予定です
'xfun::attr2()' を代わりに使って下さい
help("Deprecated") を見て下さい
| 商品名 | 売上金額合計 | 売上個数合計 |
|---|---|---|
| 緑茶 | 18057150 | 120381 |
| 濃い茶 | 12069000 | 80460 |
これで自社の製品ごとの売上金額と売上個数の合計が計算されました。 ここで注意しないといけないことは,group_by()関数とsummarise()関数を使った場合,グループごとに1つの統計量を返すため,上のコードだと, 自社の2商品ごとの売上金額と売上個数の合計が出力され,2行2列のデータフレームが返されていることが分かります。
次に,各月ごとの売上金額を計算してみましょう。 日付変数の型を確認します。
class(df$日付)[1] "POSIXct" "POSIXt"
POSIXct POSIXt という日付型のデータです。 この変数日付から月を取り出すには,lubridateパッケージを使います。 日付データは2023-05-14 UTCといった形式で格納されているため,lubridate::month()関数を使って月を取り出します。
df_month_sales <- df |>
filter(メーカー == "自社") |>
mutate(月 = lubridate::month(日付, label = TRUE)) |>
group_by(月) |> # 月ごとにグループ化
summarise(売上金額合計 = sum(金額)) |>
arrange(月) |>
ungroup()
df_month_sales |>
gt() |>
fmt_number(columns = 2:2, decimals = 0) |>
tab_header(title = "表1−5 自社商品の月ごとの売上金額") |>
gt_theme_pff() |> # テーマを適用
tab_options(
heading.title.font.size = "small",
table.font.size = "large",
table.width = pct(60)
)| 表1−5 自社商品の月ごとの売上金額 | |
|---|---|
| 月 | 売上金額合計 |
| 1 | 1,577,250 |
| 2 | 1,317,900 |
| 3 | 1,809,300 |
| 4 | 2,238,750 |
| 5 | 2,506,050 |
| 6 | 2,288,550 |
| 7 | 3,844,350 |
| 8 | 4,231,950 |
| 9 | 3,599,550 |
| 10 | 2,888,250 |
| 11 | 2,140,800 |
| 12 | 1,683,450 |
同じように各時間帯ごとの売上金額を計算してみましょう。
df_time_sales <- df |>
filter(メーカー == "自社") |>
group_by(時間) |>
summarise(売上金額合計 = sum(金額)) |>
arrange(時間) |>
ungroup()
df_time_sales |>
gt() |>
fmt_number(columns = 2:2, decimals = 0) |>
gt_theme_pff() |> # テーマを適用
tab_header(title = "表1−6 自社商品の時間帯別売上高") |>
tab_options(
heading.title.font.size = "small",
table.font.size = "large",
table.width = pct(60)
)| 表1−6 自社商品の時間帯別売上高 | |
|---|---|
| 時間 | 売上金額合計 |
| 10 | 1,506,600 |
| 11 | 2,070,750 |
| 12 | 2,942,400 |
| 13 | 2,729,550 |
| 14 | 2,108,700 |
| 15 | 2,740,050 |
| 16 | 3,033,150 |
| 17 | 3,617,700 |
| 18 | 3,038,550 |
| 19 | 2,710,950 |
| 20 | 2,124,900 |
| 21 | 1,502,850 |
1.11 集計結果をグラフで可視化
可視化はRの得意分野です。 ggplot2パッケージを使って,いろんなグラフで表示してみましょう。
ggplot2パッケージで日本語を表示させるためには,一手間必要になります。 しかもMacOSとWindowsでやり方が異なるので,注意してください。 松浦の環境はMacOSであるため,ヒラギノフォントを指定してます。 ついでに,カラーパレットもユニバーサルデザインに配慮したscale_fill_tableau(name = "Tableau 20")を指定してます。
メーカー別の売上合計金額を棒グラフにします。
df_maker_sales |>
ggplot() + aes(x = メーカー, y = 売上金額合計, fill = メーカー) +
geom_col() + theme_bw(base_family = "Noto San JP") +
scale_fill_tableau(name = "Tableau 20") # Tableau 20 パレットを適用
月別売上高を折れ線グラフにします。
df_month_sales |>
ggplot() + aes(x = 月, y = 売上金額合計, group = 1) +
geom_line() + geom_point() +
theme_bw(base_family = "HiraKakuPro-W3")
夏に売上高がピークを迎えていることが分かります。
時間帯別売上高を棒グラフにします。
df_time_sales |>
ggplot() +
aes(x = 時間, y = 売上金額合計, fill = factor(時間, levels = rev(unique(時間)))) + # 時間の順序を逆にする
geom_col() + theme_bw(base_family = "HiraKakuPro-W3") + # テーマとフォント
guides(fill = guide_legend(title = "時間帯")) +
scale_fill_viridis_d(direction = 1) # Viridis パレットを逆順に適用
12時ころと17時ころに売上高が大きくなっているので,昼食・夕食の時間帯に売上が伸びていることが分かります。
さらに,月ごと,時間ごとの棒グラフを重ねて表示してみましょう。
df_month_time_sales <- df |>
filter(メーカー == "自社") |>
mutate(月 = lubridate::month(日付, label = TRUE),
時間 = as.factor(時間)) |>
group_by(月, 時間) |>
summarise(売上金額合計 = sum(金額)) |>
arrange(月, 時間)`summarise()` has grouped output by '月'. You can override using the `.groups`
argument.
df_month_time_sales |>
ggplot() + aes(x = 月, y = 売上金額合計, fill = 時間) +
geom_col(position = "dodge") + theme_bw(base_family = "HiraKakuPro-W3") +
guides(fill = guide_legend(title = "時間帯")) +
scale_fill_viridis_d(direction = -1)
昼食時と夕食前に売上が伸びる傾向は1月から12月まで観察されていますが,その差は夏が非常に多く,冬には昼食時と夕食前とそれ以外の売上の差が小さくなっていることが分かります。
これをアニメーションにしてみましょう。 Rにはggplot2パッケージで作ったグラフをアニメーションにするgganimateパッケージがあります。 ここでは,transition_states()関数とenter_fade()関数,exit_fade()関数を使って,時間帯ごとの売上高をアニメーションで表示してみます。
-
transition_states(): アニメーションの状態を指定します。 -
enter_fade(): アニメーションの開始時のエフェクトを指定します。 -
exit_fade(): アニメーションの終了時のエフェクトを指定します。
pacman::p_load(gganimate)df_month_time_sales |>
ggplot() +
aes(x = 月, y = 売上金額合計, fill = 時間) +
geom_col(position = "dodge") +
theme_bw(base_family = "HiraKakuPro-W3") +
guides(fill = guide_legend(title = "時間帯")) +
scale_fill_viridis_d(direction = -1) +
transition_states(時間, transition_length = 2, state_length = 1) +
labs(
title = "月ごとの時間帯別売上高: 時間帯 {closest_state} 時",
x = "月",
y = "売上金額合計"
) +
enter_fade() +
exit_fade()
同じように,月と時間を入れ替えてみましょう。
df_month_time_sales |>
ggplot() +
aes(x = 時間, y = 売上金額合計, fill = 月) +
geom_col(position = "dodge") +
theme_bw(base_family = "HiraKakuPro-W3") +
guides(fill = guide_legend(title = "月")) +
scale_fill_viridis_d(direction = -1) +
transition_states(月, transition_length = 2, state_length = 1) +
labs(
title = "時間ごとの月別売上高: {closest_state} 月",
x = "時間",
y = "売上金額合計"
) +
enter_fade() +
exit_fade()
テキストの気温と販売個数の散布図は,気温データがないため作れません。
1.12 提出用の資料を作成する。
テキストではMS Excelで作成した表を、MS Powerpointに貼り付けてスライド資料を作成するようになっていますが、 RとQuartoを使えば、データ分析と資料作成を同じ場所で行うことができます。