Search code examples
rfunctional-programmingapply

How to access the function itself in apply-like functions


I want to do an apply / map function-like but using one element of the list as a operand of the calling function.

I give you better an example, let's say I want to subtract to every element of a list, the first element of the list, i.e.: x[i] = x[i] - x[1].

If I understood correctly, when calling the function with apply, the function gets the current element of the list, x[i], only as an argument, but I would need the list itself to access to the first element (x[1]) and subtract it to the current element (x[i]).

I would expect a way to provide to the applying function an extra argument or access to the list itself.


Solution

  • lapply can take multiple arguments.

    Consider list lst,

    > lst
    $X1
    [1] 1 2 3
    
    $X2
    [1] 4 5 6
    
    $X3
    [1] 7 8 9
    
    $X4
    [1] 10 11 12
    

    and first as hot element.

    > h <- 1
    

    Then we provide lst without that element as first argument to iterate over, and lst[[h]] as second argument after the function. In contrast to Map the latter will always passed as a whole.

    > lapply(lst[-h], \(x, y) x - y, l[[h]])
    $X2
    [1] 3 3 3
    
    $X3
    [1] 6 6 6
    
    $X4
    [1] 9 9 9
    

    If you aim to replace all but the hot element, do

    > lst[-h] <- lapply(lst[-h], \(x, d) x - d[[h]], lst)
    > lst
    $X1
    [1] 1 2 3
    
    $X2
    [1] 3 3 3
    
    $X3
    [1] 6 6 6
    
    $X4
    [1] 9 9 9
    

    Data:

    > dput(lst)
    list(X1 = 1:3, X2 = 4:6, X3 = 7:9, X4 = 10:12)