web-dev-qa-db-ja.com

ネストされたforループに相当するpurrrマップ

次と同等のpurrr :: mapは何ですか?

for (i in 1:4) {
  for (j in 1:6) {
    print(paste(i, j, sep = "-"))
  }
}

OR

lapply(1:4, function(i) 
  lapply(1:6, function(j) 
    print(paste(i, j, sep = "-"))))

概念的には、innerマップ関数でouterループを参照する方法がわかりません。

map(1:4, ~ map(1:6, ~ print(paste(.x, ????, sep = "-")))
17
merov

@ r2evansが指摘するように、最初の呼び出しからの.xはマスクされます。ただし、2つのパラメーター.x.yを使用するラムダ関数を作成し、.x引数を使用して以前の.yを新しい...に割り当てることができます。

walkではなくmapを使用します。この場合、副作用(印刷)のみに関心があるためです。

walk(1:4,~ walk(1:6, ~ print(paste(.x, .y, sep = "-")),.y=.x))

別のオプションは、expand.gridを使用して組み合わせをレイアウトし、pwalk(または他の状況ではpmap)を使用してそれらを反復することです

purrr::pwalk(expand.grid(1:4,1:6),~print(paste(.x, .y, sep = "-")))

どちらの場合も出力:

[1] "1-1"
[1] "2-1"
[1] "3-1"
[1] "4-1"
[1] "5-1"
[1] "6-1"
[1] "1-2"
[1] "2-2"
[1] "3-2"
[1] "4-2"
[1] "5-2"
[1] "6-2"
[1] "1-3"
[1] "2-3"
[1] "3-3"
[1] "4-3"
[1] "5-3"
[1] "6-3"
[1] "1-4"
[1] "2-4"
[1] "3-4"
[1] "4-4"
[1] "5-4"
[1] "6-4"
14

関数式(~ のようにネストしようとすると、参照するmapのレベルが完全に不明確になるため、少し制限されます。 (まあ、それは正しくありません。inside-outを参照していることは完全に明らかです。また、両方が同じ命名法を使用しているため、外部変数内部変数によってマスクされています。)

それを回避する最善の方法は、式メソッドを使用せず、代わりに即時/匿名(または事前定義)関数を使用することです。

library(purrr)
str(map(1:2, function(x) map(1:3, function(y) paste(x, y, sep = "-"))))
# List of 2
#  $ :List of 3
#   ..$ : chr "1-1"
#   ..$ : chr "1-2"
#   ..$ : chr "1-3"
#  $ :List of 3
#   ..$ : chr "2-1"
#   ..$ : chr "2-2"
#   ..$ : chr "2-3"
21
r2evans

ただ今これを実行しています。

walk(1:4,~ walk(1:6, ~ print(paste(.x, .y, sep = "-")),.y=.x)) 
[1] "1-1"
[1] "2-1"
[1] "3-1"
[1] "4-1"
[1] "5-1"
[1] "6-1"
[1] "1-2"

そして

purrr::pwalk(expand.grid(1:4,1:6),~print(paste(.x, .y, sep = "-")))
[1] "1-1"
[1] "2-1"
[1] "3-1"
[1] "4-1"
[1] "1-2"

しかし、ネストされたforループと正確に一致させると、いじられてこれが機能します。

for (i in 1:4) {
  for (j in 1:6) {
    print(paste(i, j, sep = "-"))
  }
}
[1] "1-1"
[1] "1-2"
[1] "1-3"
[1] "1-4"
[1] "1-5"
[1] "1-6"
[1] "2-1"

purrr::pwalk(expand.grid(1:6,1:4),~print(paste(.y, .x, sep = "-")))
[1] "1-1"
[1] "1-2"
[1] "1-3"
[1] "1-4"
[1] "1-5"
[1] "1-6"
[1] "2-1"

#or even a map of this
walk(1:4,~ walk(1:6, ~ print(paste(.y, .x, sep = "-")),.y=.x))

なぜ.y=.xは最後です。

1
Shadowhawk