Why?

December 14, 2010

Logical operators in R

Filed under: R — Tags: , , , — csgillespie @ 4:38 pm

A logical operator

In R, the operators “|” and “&” indicate the logical operations OR and AND. For example, to test if x equals 1 and y equals 2 we do the following:

> x = 1; y = 2
> (x == 1) & (y == 2)
[1] TRUE

However, if you are used to programming in C you may be tempted to write

#Gives the same answer as above (in this example...)
> (x == 1) && (y == 2)
[1] TRUE

At this point you could be lulled into a false sense of security and believe that they could be used interchangeably. Big mistake.

Let’s consider another example, this time a vector comparison:

> z = 1:6
> (z > 2) & (z < 5)
[1] FALSE FALSE TRUE TRUE FALSE FALSE
> z[(z>2) & (z<5)]
[1] 3 4

but the double “&&” gives

> (z > 2) && (z < 5)
[1] FALSE
> z[(z > 2) && (z < 5)]
integer(0)#Probably not what you want

It’s all gone a bit pear shaped! In fact it could have been worse:

> (z > 2) && (z < 5)
[1] TRUE
> z[(z > 0) && (z < 5)]
[1] 1 2 3 4 5 6

Now you’ve the wrong answer and something that would be very tricky to spot. This is because R recylces the TRUE variable.

What’s the difference?

Well from the R help page:

“The longer form evaluates left to right examining only the first element of each vector”

where the longer form refers to “&&”.  So

> (z > 2) && (z < 5)
[1] FALSE

is equivalent to:

> (z[1] > 2) & (z[1] < 5)
[1] FALSE

The same concept applies to the OR operator, “|”.

As the commentators point out below, another key difference is for the longer form

“Evaluation proceeds only until the result is determined”

This concept is highlighted in the following example:

> f = function(){cat("My name is f\n");return(TRUE)}
> g = function(){cat("My name is g\n");return(FALSE)}
> f() | g()
My name is f
My name is g
[1] TRUE
> f() || g()
My name is f
[1] TRUE

This has two benefits:

  • Evaluation will be faster. In the above example, the function g isn’t evaluated (thanks to Andrew Robson and NotMe)
  • Also, you can use the double variety to check a property of a data structure before carrying on with your analysis, i.e. all(!is.na(x)) && mean(x) > 0 (thanks to Pat Burns for this tip)
Advertisements

5 Comments »

  1. Hi Colin,

    X || Y performs sequential evaluation of X and Y.

    From p. 22 of our lovely book[1] … X || Y is useful when Y is not always well-defined. Also, if Y takes a while to evaluate.

    There are reasonably easy work-arounds for both conditions, but || and && provide a compact representation.

    Best wishes

    Andrew

    [1] “Introduction to Scientific Programming and Simulation using R“, 2009, Chapman & Hall.

    Comment by Andrew Robinson — December 15, 2010 @ 3:20 am

  2. As is mentioned on ?”&&” you mainly use && in if-clauses. So something like if ((a==3) && (b==4) && (d==7)). So if (a==3) is NOT true, then R doesn’t need to look whether b==4 or d==7. Should be faster.

    Comment by NotMe — December 15, 2010 @ 8:06 am

  3. As an example of what the previous comments are talking about, you might have something like:

    if(all(!is.na(x)) && mean(x) > 0) { …

    The first part about missing values makes sure that you don’t run into trouble with the test on the mean (which is what you really care about).

    Comment by Pat Burns — December 15, 2010 @ 9:44 am

  4. Many thanks for your helpful comment. I’ve updated the post accordingly.

    Comment by csgillespie — December 15, 2010 @ 5:03 pm

  5. I think && and || have been badly implemented. In other languages they the conditional AND and OR operators, they perform a logical AND or OR boolean operations , but only evaluate its second operand if necessary.

    Comment by joe — November 28, 2016 @ 6:50 pm


RSS feed for comments on this post. TrackBack URI

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s

Blog at WordPress.com.

%d bloggers like this: