purrr累积函数奇怪的输出

时间:2019-06-02 01:12:40

标签: r purrr

我想这是两个问题的结合。

我试图理解purrr::accumulate函数,但是很难弄清.x.y之间的相互作用。我一直在阅读purrr小插图,但解释不多。我没有编程背景,所以很多事情困扰着我。

第一件事,为什么它们在相同的调用中会有不同的输出?唯一的区别是()之后的paste

accumulate(letters[1:5], paste, sep = ".")
[1] "a"         "a.b"       "a.b.c"     "a.b.c.d"   "a.b.c.d.e"

accumulate(letters[1:5], paste(), sep = ".")
[1] "a" "a" "a" "a" "a"

第二,这是怎么回事?

2:11 %>% accumulate(~ .x)
[1] 2 2 2 2 2 2 2 2 2 2

accumulate(1:5, `+`)
[1]  1  3  6 10 15

2:11 %>% accumulate(~ .y)
[1]  2  3  4  5  6  7  8  9 10 11

2:11 %>% accumulate(~ .x + .y)
[1]  2  5  9 14 20 27 35 44 54 65

.x是累加值,但我想它没有累加任何值?对于1:5cumsum来说,这是有意义的。 .y是列表中的元素。我将.y解释为本质上是print正确吗?

但是.x + .y的第一个输出不是4吗?

一些见识会受到欢迎。

1 个答案:

答案 0 :(得分:1)

当有print条语句时,会更容易理解

2:11 %>% 
   accumulate(~ {
     print("---step----")
     print(paste0(".x: ", .x))
     print(paste0(".y: ", .y))
     print(.x + .y)
    })
#[1] "---step----"
#[1] ".x: 2"  # .init or first value of the vector (as `.init` not specified)
#[1] ".y: 3"  # second value
#[1] 5    # sum of .x + .y
#[1] "---step----"
#[1] ".x: 5"   # note .x gets updated with the sum
#[1] ".y: 4"   # .y gets the next element
#[1] 9
#[1] "---step----"
#[1] ".x: 9"   # similarly in all the below steps
#[1] ".y: 5"
#[1] 14
#[1] "---step----"
#[1] ".x: 14"
#[1] ".y: 6"
#[1] 20
#[1] "---step----"
#[1] ".x: 20"
#[1] ".y: 7"
#[1] 27
#[1] "---step----"
#[1] ".x: 27"
#[1] ".y: 8"
#[1] 35
#[1] "---step----"
#[1] ".x: 35"
#[1] ".y: 9"
#[1] 44
#[1] "---step----"
#[1] ".x: 44"
#[1] ".y: 10"
#[1] 54
#[1] "---step----"
#[1] ".x: 54"
#[1] ".y: 11"
#[1] 65
# [1]  2  5  9 14 20 27 35 44 54 65

在这里,.x是在每次迭代中更新的那个,并且该值正在传递到.x + .y

它本质上类似于

cumsum(2:11)
#[1]  2  5  9 14 20 27 35 44 54 65

当我们仅传递.x时,它就是.init的值,即第一个元素没有更新,因为.f没有做任何事情

2:11 %>% 
    accumulate(~ print(.x))
#[1] 2
#[1] 2
#[1] 2
#[1] 2
#[1] 2
#[1] 2
#[1] 2
#[1] 2
#[1] 2
# [1] 2 2 2 2 2 2 2 2 2 2

现在,我们为.init传递一个不同的值

2:11 %>%
    accumulate(~ print(.x), .init = 5)
#[1] 5
#[1] 5
#[1] 5
#[1] 5
#[1] 5
#[1] 5
#[1] 5
#[1] 5
#[1] 5
#[1] 5
#[1] 5 5 5 5 5 5 5 5 5 5 5

另外,前两个调用的区别在于传递参数的区别。在第一种情况下,paste.x.y被隐式传递,而在第二种情况paste()中,仅是.x,即进入其中< / p>

accumulate(letters[1:5], ~paste(.x, .y, sep = "."))
#[1] "a"         "a.b"       "a.b.c"     "a.b.c.d"   "a.b.c.d.e"
accumulate(letters[1:5], ~paste(.x,  sep = "."))
#[1] "a" "a" "a" "a" "a"