Search code examples
rlapplymatchingsapplymapply

R: use of match.fun over sapply, lapply and mapply


I'm not sure if my usage of match.fun is correct of not for this case. (I don't want to use for loop because it takes time).

I have a data frame like this.

df <- data.frame(client = c("A", "B", "C", "D"), 
                 fun = c("bill1stEvent_OT", "bill1stEvent_Tour", "billCreation_OT", "bill1stEvent_Tour_LoadingSite"), 
                 agency = c("NA", "NA", "Agency_A", "NA"), 
                 loading_site = c("NA", "NA", "NA", "Paris"))

>df
  client                            fun    agency  loading_site
       A                bill1stEvent_OT        NA            NA
       B              bill1stEvent_Tour        NA            NA
       C                billCreation_OT  Agency_A            NA
       D  bill1stEvent_Tour_LoadingSite        NA         Paris

The fun column contains functions I created. Every function takes the same argument: client, agency, loading_site year and month. So the way you read this table is, for example, for the client C, apply function billCreation_OT with arguments agency = Agency_A and loading_site = NULL. Each function returns a data frame.

I have a list of clients I want to apply functions, I also set the arguments year and month. :

client_list <- c("A", "C")
year <- "2018"
month <- "07"

Question: How can I call this table and apply functions with the corresponding arguments with just "one go"? So with the client_list above, what I want to do is to run these two functions below and store the result(data frames) in a list(or whatever possible).

bill1stEvent_OT(client = "A", agency = NULL, loading_site = NULL)
billCreation_OT(client = "C", agency =  Agency_A, loading_site = NULL)

My attempt:

fun_to_apply <- df[df$client %in% client_list, ]$fun
agency_arg <- df[df$client %in% client_list, ]$agency
loading_site_arg <- df[df$client %in% client_list, ]$loading_site

sapply(X = lapply(fun_to_apply, match.fun), 
       FUN = mapply,
       year = year,
       month = month,
       agency = agency_arg,
       loading_site = loading_site_arg)

Error in (function (client, year, month) : 
 arguments inutilisés (agency = dots[[3]][[1]], loading_site = dots[[4]][[1]])

I also don't know how to pass to the functions arguments agency and loading_site as NULL. When you read the data frame it evaluates NA as string like "NA" I guess.

Thanks for any help!


Solution

  • To illustrate my "can be done" comment:

    # inputs
    client_list <- c("A", "C")
    year <- "2018"
    month <- "07"
    
    # dummy functions
    bill1stEvent_OT <- function(agency, loading_site){paste("11", year, month, agency, loading_site)}
    bill1stEvent_Tour <- function(agency, loading_site){paste("22", year, month, agency, loading_site)}
    billCreation_OT <- function(agency, loading_site){paste("33", year, month, agency, loading_site)}
    bill1stEvent_Tour_LoadingSite <- function(agency, loading_site){paste("44", year, month, agency, loading_site)}
    
    
    # loop through rows, match function name
    apply(df, 1, function(i){
      # we can add a step to convert "NA" to actual NA.
      if(i[1] %in% client_list){
             match.fun(i[2])(agency = i[3], loading_site = i[4])
        } else {NA}
    })
    
    # [1] "11 2018 07 NA NA"       NA                       "33 2018 07 Agency_A NA" NA                      
    

    Having shown the possible way, I would not recommend using this. There are better ways if you can tell us more about the problem.