2017-08-14 55 views
1

我有一個自定義函數,它彙總了一個變量。 我簡化了函數來說明我的問題,即它比下面顯示的更復雜。請注意,該函數的一般結構應該保持不變:它需要一個參數來指定要使用哪個數據幀(df)以及一個變量進行彙總的參數(variable_to_test)。lapply函數帶有數據幀和變量的參數

my_fun <- function(df, variable_to_test) { 

    variable_to_test <- enquo(variable_to_test) 
    new_var_name <- paste0(quo_name(variable_to_test), "_new_name") 

    df %>% 
    summarise(
     !!new_var_name := sum(!!variable_to_test, na.rm = TRUE) 
    ) 
} 

使用一個例子,我可以申請在每個變量的函數在我的數據幀:

library(tidyverse) 
dat <- tibble(
    variable_1 = c(1:5, NA, NA, NA, NA, NA), 
    variable_2 = c(NA, NA, NA, NA, NA, 11:15) 
) 


> my_fun(dat, variable_1) 
# A tibble: 1 x 1 
    variable_1_new_name 
       <int> 
1     15 


> my_fun(dat, variable_2) 
# A tibble: 1 x 1 
    variable_2_new_name 
       <int> 
1     65 

但是:我怎麼能列出適用於在數據幀中的所有列的功能?我試過

> dat %>% 
+ lapply(., my_fun) 
Error in duplicate(quo) : argument "quo" is missing, with no default 
Called from: duplicate(quo) 

但是這會返回一個錯誤。我正在努力處理這個事實,即該函數爲要處理的數據框以及要彙總的變量提供參數。請注意,我想保留這種結構 - 我發現將數據框的名稱傳遞給函數會更優雅,而不僅僅是將函數的變量名稱和數據框「硬編碼」到函數體中。有沒有人有一個好主意如何lapply()的功能?

+1

您是否需要'dplyr'解決方案,還是基礎R適合您的需求?通常你可以通過給函數一個靜態和一個可變的輸入來解決這個問題,例如, 'lapply(dat,function(x)myfun(dat,x))'。我不熟悉'dplyr',但也許嘗試'lapply(。,function(x)myfun(。,x))'? – LAP

+0

我已經有了一個基礎R解決方案。我試圖重寫'tidyeval'方式的函數,因爲它提高了函數體的可讀性。所以是的,我需要一個'tidyeval'解決方案:) – piptoma

回答

2

哦,我覺得你只是在錯誤的東西映射。對於tidyverse解決方案,我會嘗試:

map(dat, ~my_fun(dat, .)) 

這樣做是什麼地圖上的列名,並插上列到.

1

您正在錯誤的級別工作。如果您將功能映射到數據框上,則此功能應採用。這裏的問題是函數my_fun()需要一個數據框而不是一列。

您需要找到解決問題的其他方法。一種解決方案是使用由dplyr提供的映射器:

dat %>% 
    summarise_all(sum, na.rm = TRUE) %>% 
    rename_all(paste0, "_new_name") 

你可以同樣使用的map()set_names()組合從purrr。

dat %>% 
    map_df(sum, na.rm = TRUE) %>% 
    set_names(paste0, "_new_name")