Anoushiravan R
Anoushiravan R

Reputation: 21918

predicate function in map

I have been studying purrr family functions recently and while I was reading the documentation of map_if I came across an alternative definition form for .p argument aka. predicate function that I could not understand. It say:

"Alternatively, if the elements of .x are themselves lists of objects, a string indicating the name of a logical element in the inner lists"

I was wondering if someone could tell me what it means and how I can go about using it while I deal with a list whose elements are also lists. Something like this:

x <- list(a = list(foo = 1:2, bar = 3:4), b = list(baz = 5:6))

A simple example would be much appreciated as I've done some research and could not find any indication of it.

Thank you very much in advance.

Upvotes: 1

Views: 417

Answers (2)

c-petersen
c-petersen

Reputation: 46

It seems to refer to an inner variable name with a TRUE/FALSE value. Here is the basic example I created to test it.

Create a list where the inner list has boolean values for one variable:

A <- list(foo=list(x=1, y=TRUE), bar=list(x=2, y=FALSE))

Reference the boolean variable (y) as the .p predicate by passing a string with the variable name:

map_if(A, "y", as.character)

$foo
[1] "1"    "TRUE"

$bar
$bar$x
[1] 2

$bar$y
[1] FALSE

So, it only modified the foo variable since y was TRUE and bar wasn't altered since y was FALSE.

Upvotes: 1

AnilGoyal
AnilGoyal

Reputation: 26218

Though I am not fully sure what actually you want to understand, but taking the case of list of lists, we need to consider that here only map_if is available and pmap_if is not available. Let's take another list of lists than you have suggested.

x <- list(a = list(foo = 1:2, bar = 3:4), b = list(baz = 5:6), c = list(bird = 7:10))

Now map_if applies .f wherever .p is T. So if we want to take mean of all odd indexed lists in list x, we have to actually use nested map again.

see

map_if(x, as.logical(seq_along(x) %% 2) , ~map(.x, ~mean(.x)))

$a
$a$foo
[1] 1.5

$a$bar
[1] 3.5


$b
$b$baz
[1] 5 6


$c
$c$bird
[1] 8.5

we may also other predicate functions in .p. The below example produces same output.

map_if(x, names(x) %in% c("a", "c") , ~map(.x, ~mean(.x)))

Or if let's say x is named something like this

x <- list(val1 = list(foo = 1:2, bar = 3:4), ind1 = list(baz = 5:6), val2 = list(bird = 7:10))

then below syntax will produce similar results

map_if(x, str_detect(names(x), "val") , ~map(.x, ~mean(.x)))

I hope this is somewhat near to you may want to understand.

P.S. You can give it a read too.

Upvotes: 1

Related Questions