为什么 colnames 函数在与管道运算符和 [ 选择器一起使用时会生成小标题(而不是向量?
Why does the colnames function generate a tibble (and not a vector), when used with the pipe operator and [ selector?
问题:为什么 colnames
函数在与管道运算符 %>%
和 [
选择器一起使用时会生成小标题?
示例:给定以下小标题:
library(tidyverse)
x <- tribble(
~a, ~b,
1, 0,
0, 1
)
问题:当与管道运算符和 [
选择器一起使用时,colnames 函数会生成一个 tibbe:
x %>% colnames(.)[1]
#> # A tibble: 2 x 1
#> a
#> <dbl>
#> 1 NA
#> 2 NA
而我希望它生成一个向量,就像没有使用管道运算符一样:
colnames(x)[1]
#> [1] "a"
我们可以在 colnames
之后使用 first
x %>%
colnames %>%
first
#[1] "a"
或者在 {}
中阻塞整个表达式以作为单个表达式求值并避免运算符
的优先级
x %>%
{colnames(.)[1]}
#[1] "a"
管道将左侧插入到右侧主函数的第一个参数中,在本例中为 [ 。那就是这三个是一样的:
x %>% colnames(.)[1]
x %>% `[`(colnames(.), 1)
x %>% `[`(., colnames(.), 1)
最后一个是相同的,因为如果 main 函数的参数之一是点,它不会插入左侧。
要防止它插入点,请使用 {...}
x %>% { colnames(.)[1] }
或使用:
x %>% colnames %>% .[1]
或使用dplyr::first
或dplyr::slice_head(n = 1)或dplyr::nth(1)或purrr::pull(1)
或magrittr::extract(1)
或head(1)
x %>% colnames %>% first
因为%>%
自动插入.
作为右侧的第一个参数,除非.
已经被用作顶级参数右侧.
您的右侧是 colnames(.)[1]
— .
是 而不是 此处的顶级参数。事实上,表达式 colnames(.)[1]
完全等同于
`[`(colnames(.), 1)
所以这个表达式的顶层参数是colnames(.)
和1
。 .
也不是。所以 %>%
将你的表达式转换为
`[`(x, colnames(x), 1)
再次等同于
x[colnames(x), 1]
那个表达式并没有真正的意义,恰好导致了你所观察到的结果。
要避免 .
自动插入,您可以将表达式包装到 {…}
中,如 akrun 所示。或者您可以将复合表达式拆分为其组成部分:
x %>% colnames() %>% `[`(1L)
问题:为什么 colnames
函数在与管道运算符 %>%
和 [
选择器一起使用时会生成小标题?
示例:给定以下小标题:
library(tidyverse)
x <- tribble(
~a, ~b,
1, 0,
0, 1
)
问题:当与管道运算符和 [
选择器一起使用时,colnames 函数会生成一个 tibbe:
x %>% colnames(.)[1]
#> # A tibble: 2 x 1
#> a
#> <dbl>
#> 1 NA
#> 2 NA
而我希望它生成一个向量,就像没有使用管道运算符一样:
colnames(x)[1]
#> [1] "a"
我们可以在 colnames
first
x %>%
colnames %>%
first
#[1] "a"
或者在 {}
中阻塞整个表达式以作为单个表达式求值并避免运算符
x %>%
{colnames(.)[1]}
#[1] "a"
管道将左侧插入到右侧主函数的第一个参数中,在本例中为 [ 。那就是这三个是一样的:
x %>% colnames(.)[1]
x %>% `[`(colnames(.), 1)
x %>% `[`(., colnames(.), 1)
最后一个是相同的,因为如果 main 函数的参数之一是点,它不会插入左侧。
要防止它插入点,请使用 {...}
x %>% { colnames(.)[1] }
或使用:
x %>% colnames %>% .[1]
或使用dplyr::first
或dplyr::slice_head(n = 1)或dplyr::nth(1)或purrr::pull(1)
或magrittr::extract(1)
或head(1)
x %>% colnames %>% first
因为%>%
自动插入.
作为右侧的第一个参数,除非.
已经被用作顶级参数右侧.
您的右侧是 colnames(.)[1]
— .
是 而不是 此处的顶级参数。事实上,表达式 colnames(.)[1]
完全等同于
`[`(colnames(.), 1)
所以这个表达式的顶层参数是colnames(.)
和1
。 .
也不是。所以 %>%
将你的表达式转换为
`[`(x, colnames(x), 1)
再次等同于
x[colnames(x), 1]
那个表达式并没有真正的意义,恰好导致了你所观察到的结果。
要避免 .
自动插入,您可以将表达式包装到 {…}
中,如 akrun 所示。或者您可以将复合表达式拆分为其组成部分:
x %>% colnames() %>% `[`(1L)