Home > Enterprise >  call a function based on variable
call a function based on variable

Time:02-04

i have a dataframe like this:

NAME    ALPHA   BETA    GAMMA DELTA CONSTANT    FUNCTION   ANSWER

A   1   2   3   4   5   F1

B   6   7   8   9   10  F2

C   11  12  13  14  15  F3

D   16  17  18  19  20  F4

E   20  21  22  23  24  F5

F   25  26  27  28  29  F6

G   0.3 0.7 1.0 1.3 1.7 F1

H   2.0 2.3 2.7 3.0 3.3 F2

I   3.7 4.0 4.3 4.7 5.0 F3

J   5.3 5.7 6.0 6.3 6.7 F4

K   6.7 7.0 7.3 7.7 8.0 F5

L   8.3 8.7 9.0 9.3 9.7 F6

M   0.1 0.2 0.3 0.4 0.6 F1

The function i need to apply is defined in the Function column.

Function are predefined equations such as

F1<- function(ALPHA,BETA,GAMMA,DELTA,CONSTANT){
  ((ALPHA * CONSTANT^ 2)   (BETA * SPEED)   GAMMA  (DELTA * LOG(CONSTANT)) 
}

I want to be able apply the equation in Function column for each row and the result should go into the answer column.

we have a few thousand rows and there are around 50 types of functions.

Is there a way to do this?

Many thanks

CodePudding user response:

As long as you have all the functions defined, you can call them by name using do.call on a list of the arguments. You can therefore do this row-wise in your data frame, for example using sapply:

# Modify the original function slightly, as there is no variable called SPEED
F1 <- function(ALPHA,BETA,GAMMA,DELTA,CONSTANT){
  ((ALPHA * CONSTANT^ 2)   (BETA * 3)   GAMMA   (DELTA * log(CONSTANT))) 
}

# For the sake of the example, we will make F2 to F6 the same as F1
# But note these functions could all be different
F2 <- F3 <- F4 <- F5 <- F6 <- F1

df$answer <- sapply(seq(nrow(df)), 
                    function(i) do.call(df$FUNCTION[i], as.list(df[i, 2:6])))

df
#>    NAME ALPHA BETA GAMMA DELTA CONSTANT FUNCTION       answer
#> 1     A   1.0  2.0   3.0   4.0      5.0       F1 4.043775e 01
#> 2     B   6.0  7.0   8.0   9.0     10.0       F2 6.497233e 02
#> 3     C  11.0 12.0  13.0  14.0     15.0       F3 2.561913e 03
#> 4     D  16.0 17.0  18.0  19.0     20.0       F4 6.525919e 03
#> 5     E  20.0 21.0  22.0  23.0     24.0       F5 1.167810e 04
#> 6     F  25.0 26.0  27.0  28.0     29.0       F6 2.122428e 04
#> 7     G   0.3  0.7   1.0   1.3      1.7       F1 4.656817e 00
#> 8     H   2.0  2.3   2.7   3.0      3.3       F2 3.496177e 01
#> 9     I   3.7  4.0   4.3   4.7      5.0       F3 1.163644e 02
#> 10    J   5.3  5.7   6.0   6.3      6.7       F4 2.730003e 02
#> 11    K   6.7  7.0   7.3   7.7      8.0       F5 4.731117e 02
#> 12    L   8.3  8.7   9.0   9.3      9.7       F6 8.371778e 02
#> 13    M   0.1  0.2   0.3   0.4      0.6       F1 7.316698e-01

Created on 2022-02-04 by the reprex package (v2.0.1)


DATA USED

df <- structure(list(NAME = c("A", "B", "C", "D", "E", "F", "G", "H", 
"I", "J", "K", "L", "M"), ALPHA = c(1, 6, 11, 16, 20, 25, 0.3, 
2, 3.7, 5.3, 6.7, 8.3, 0.1), BETA = c(2, 7, 12, 17, 21, 26, 0.7, 
2.3, 4, 5.7, 7, 8.7, 0.2), GAMMA = c(3, 8, 13, 18, 22, 27, 1, 
2.7, 4.3, 6, 7.3, 9, 0.3), DELTA = c(4, 9, 14, 19, 23, 28, 1.3, 
3, 4.7, 6.3, 7.7, 9.3, 0.4), CONSTANT = c(5, 10, 15, 20, 24, 
29, 1.7, 3.3, 5, 6.7, 8, 9.7, 0.6), FUNCTION = c("F1", "F2", 
"F3", "F4", "F5", "F6", "F1", "F2", "F3", "F4", "F5", "F6", "F1"
)), class = "data.frame", row.names = c(NA, -13L))

CodePudding user response:

Let say df is your dataframe, and you have all the functions F1, F2, F3, F4, F5 well defined. Note, this requires that all the functions have signatures that can accept these five parameters, and are well defined. For example, if I adjust your F1 function (replace LOG with log, and parameter SPEED=0, and for illustrative purposes only, set F2, F3, F4, and F5, all to be the same function (I understand all yours will be different functions), the the following code

library(data.table)
setDT(df)

# fix F1
F1<- function(ALPHA,BETA,GAMMA,DELTA,CONSTANT, SPEED=0) {
  ((ALPHA * CONSTANT^ 2)   (BETA * SPEED)   GAMMA   (DELTA * log(CONSTANT)))
}

# for illustration, defined all other function as F1
F2 <- F3 <- F4 <-F5 <- F6 <-  F1

# get answer, by row
df[, ANSWER:=get(FUNCTION)(ALPHA, BETA, GAMMA, DELTA, CONSTANT), by=seq(1,nrow(df))]

will produce the following output

    NAME ALPHA BETA GAMMA DELTA CONSTANT FUNCTION       ANSWER
 1:    A   1.0  2.0   3.0   4.0      5.0       F1 3.443775e 01
 2:    B   6.0  7.0   8.0   9.0     10.0       F2 6.287233e 02
 3:    C  11.0 12.0  13.0  14.0     15.0       F3 2.525913e 03
 4:    D  16.0 17.0  18.0  19.0     20.0       F4 6.474919e 03
 5:    E  20.0 21.0  22.0  23.0     24.0       F5 1.161510e 04
 6:    F  25.0 26.0  27.0  28.0     29.0       F6 2.114628e 04
 7:    G   0.3  0.7   1.0   1.3      1.7       F1 2.556817e 00
 8:    H   2.0  2.3   2.7   3.0      3.3       F2 2.806177e 01
 9:    I   3.7  4.0   4.3   4.7      5.0       F3 1.043644e 02
10:    J   5.3  5.7   6.0   6.3      6.7       F4 2.559003e 02
11:    K   6.7  7.0   7.3   7.7      8.0       F5 4.521117e 02
12:    L   8.3  8.7   9.0   9.3      9.7       F6 8.110778e 02
13:    M   0.1  0.2   0.3   0.4      0.6       F1 1.316698e-01
  •  Tags:  
  • Related