2017-10-13 113 views
2

我從dplyr使用%>%margritr奮力管的東西的功能過濾器內的另一個理由。管道里面dplyr點::過濾

我會認爲這應該工作:

library(dplyr) 
library(margritr) 

d <- data.frame(a=c(1,2,3),b=c(4,5,6)) 
c(2,2) %>% filter(d, a %in% .) 

但我得到這個:

# Error in UseMethod("filter_") : 
# no applicable method for 'filter_' applied to an object of class "c('double', 'numeric')" 

我希望它在相同的方式工作,因爲這:

filter(d, a %in% c(2,2)) 
# a b 
# 1 2 5 

我在做什麼錯?

+2

我認爲這是管是如何設計的,即,它把以前輸出到下一個函數的第一個參數。你可能會需要更明確的,比如'C(2,2)%>%的過濾器(。數據= d,等等...' –

+1

你怎麼樣試試這個,而不是 'd%>%過濾器(%在%C(2,2))' – Kay

+0

我知道,'d%>%過濾器)(單位:%C(2,2%)'的作品。但我展示一個玩具例子,在現實中我的C(2 ,2)更復雜,並且它是其他一些東西的輸出。這就是我想要管的東西。 – Bruno

回答

2

管道被設計爲當你傳遞它時圍繞它的第一個參數組成函數。當你想規避這種行爲時,你可以生成一個更加靈活的匿名環境。你用花括號來做這件事,就像你在寫一個函數一樣。

5 %>% 
    {filter(iris, Sepal.Length == .)} 

爲什麼這個作品,寫{somefunctions(x, y)}相當於寫function(...) {somefunctions(x, y)}。所以上面的函數忽略了它的參數,只是在它的環境中評估變量。 .代名詞是由管道定義的,它在全球環境中搜索其他變量(如iris)。

+1

太棒了,所以在我的情況下,它會是'c(2,2)%>%{filter(d,a%in%。)}',這很有效! ' – Bruno

0

它默認管道的第一個參數。圍繞它的唯一方法是命名明確的第一個參數:

c(2,2) %>% 
    filter(.data = d, a %in% .) 

但看起來這並不能很好地工作:

a b 
1 2 5 
Warning message: 
In (~.) & (~a %in% .) : 
    longer object length is not a multiple of shorter object length 

附:你不需要明確地加載magrittr,因爲%>%已經在dplyr

+0

很奇怪我認爲整點點是能夠管到我想要的任何參數 – Bruno

+0

管道的主要規則是它總是映射到第一個參數,除非您明確指定第一個參數rg到別的東西。 – Zafar