R×purrr::reduce リストまたはベクトルの要素を累積計算した結果を取得する

R言語で、リストまたはベクトルの要素を累積計算した結果を取得する方法について解説します。ここではtidyverseパッケージに含まれているpurrrパッケージのreduce()を使用した方法についてお伝えします。

reduce()の概要

reduce()は、リストまたはベクトルの要素を累積計算した結果を取得するための関数です。reduce()は、ベクトルの要素を単一の値に結合する演算です。この結合は、2つの値を受け取り単一の値を返す二項関数.fによって実行されます。fを1:3で縮減すると、値f(f(1, 2), 3)が計算されます。

reduce()の使い方


reduce(.x, .f, ..., .init, .dir = c("forward", "backward"))

reduce2(.x, .y, .f, ..., .init)

reduce()の引数

.x

リストまたはベクトルを指定します。

.f

reduce()は2つの引数を持つ関数を指定します。関数には、第1引数として累積値が、第2引数として次の値が渡されます。
reduce2()は3つの引数を持つ関数を指定します。関数には、第1引数として累積値が、第2引数として.xの次の値、第3引数として.yの次の値が渡されます。
.fがdone()でラップされた値を返す場合、reduceは早期に終了します。

reduce関数に渡される追加の引数を指定します。
.fに追加の(定数)引数を渡す際に…を使用することは、現在では一般的に推奨されていません。代わりに、省略形の匿名関数を使用してください。


# 下記の代わりに
x |> reduce(f, 1, 2, collapse = ",")
# 以下のようにしてください。
x |> reduce(\(x, y) f(x, y, 1, 2, collapse = ","))

これにより、どの引数がどの関数に属しているかがわかりやすくなり、エラーメッセージもわかりやすくなります。

.init

指定されている場合、.x[[1]]ではなく、累積を開始する最初の値として使用されます。これは、.xが空の場合にreduceが正しい値を返すことを保証したい場合に便利です。指定されていない場合、.xが空であればエラーが発生します。

.dir = c(“forward”, “backward”)

蓄積方向を表す文字列を指定します。
「forward」(デフォルト)または「backward」のいずれかを指定します。

.y

reduce2()の場合、.fに渡される追加の引数です。initが設定されていない場合、.yは.xより1要素短くする必要があります。

準備

あらかじめ、tidyverseパッケージを読み込んでおきます。


library(tidyverse)

使用例

複数のデータフレームをleft_joinするには次のようにします。


df1 <- data.frame(x = 1:5, a = letters[1:5])
df2 <- data.frame(x = 1:5, b = LETTERS[1:5])
df3 <- data.frame(x = 1:5, c = c("あ", "い", "う", "え", "お"))
reduce(list(df1, df2, df3), ~ left_join(..1, ..2, by = join_by(x))) 

  x a b  c
1 1 a A あ
2 2 b B い
3 3 c C う
4 4 d D え
5 5 e E お