R Tip: use `isTRUE()`

.

A lot of R functions are *type unstable*, which means they return different types or classes depending on details of their values.

For example consider `all.equal()`

, it returns the logical value `TRUE`

when the items being compared are equal:

all.equal(1:3, c(1, 2, 3)) # [1] TRUE

However, when the items being compared are not equal `all.equal()`

instead returns a message:

all.equal(1:3, c(1, 2.5, 3)) # [1] "Mean relative difference: 0.25"

This can be inconvenient in using functions similar to `all.equal()`

as tests in `if()`

-statements and other program control structures.

The saving functions is `isTRUE()`

. `isTRUE()`

returns `TRUE`

if its argument *value* is equivalent to `TRUE`

, and returns `FALSE`

otherwise. `isTRUE()`

makes `R`

programming much easier.

Some examples of `isTRUE()`

are given below:

isTRUE(TRUE) # [1] TRUE isTRUE(FALSE) [1] FALSE isTRUE(NULL) # [1] FALSE isTRUE(NA) # [1] FALSE isTRUE(all.equal(1:3, c(1, 2.5, 3))) # [1] FALSE isTRUE(all.equal(1:3, c(1, 2, 3))) # [1] TRUE lst <- list(x = 5) isTRUE(lst$y == 7) # [1] FALSE lst$y == 7 logical(0) isTRUE(logical(0)) # [1] FALSE

Using `isTRUE()`

one can write safe and legible code such as the following:

# Pretend this assignment was performed by somebody else. lst <- list(x = 5) # Our own sanitization code. if(!isTRUE(lst$y > 3)) { lst$y = lst$x } print(lst) # $x # [1] 5 # # $y # [1] 5

`R`

now also has `isFALSE()`

, but by design it does not mean the same thing as `!isTRUE()`

. The ideas is: for a value `v`

at most of one of `isTRUE()`

or `isFALSE()`

is set, and both are non-NA unnamed scalar logical values. (example: `isTRUE(5)`

, `isFALSE(5)`

).

Or as `help(isTRUE)`

puts it:

… if(isTRUE(cond)) may be preferable to if(cond) …

Note: prior to `R`

3.5 `isTRUE`

(the current version!) was defined as “`isTRUE <- function(x) identical(x, TRUE)`

” (please see change-log here). This seemed clever, but failed on named logical values (violating a principle of least surprise):

oldTRUE <- function(x) identical(x, TRUE) v <- TRUE oldTRUE(v) # [1] TRUE isTRUE(v) # [1] TRUE names(v) <- "condition" oldTRUE(v) # [1] FALSE isTRUE(v) # [1] TRUE

This caused a lot of problems (example taken from R3.5.0 NEWS):

x <- rlnorm(99) isTRUE(median(x) == quantile(x)["50%"]) # [1] TRUE oldTRUE(median(x) == quantile(x)["50%"]) # [1] FALSE

Categories: Programming Tutorials

### jmount

Data Scientist and trainer at Win Vector LLC. One of the authors of Practical Data Science with R.