How to catch integer(0)?

137,532

Solution 1

That is R's way of printing a zero length vector (an integer one), so you could test for a being of length 0:

R> length(a)
[1] 0

It might be worth rethinking the strategy you are using to identify which elements you want, but without further specific details it is difficult to suggest an alternative strategy.

Solution 2

If it's specifically zero length integers, then you want something like

is.integer0 <- function(x)
{
  is.integer(x) && length(x) == 0L
}

Check it with:

is.integer0(integer(0)) #TRUE
is.integer0(0L)         #FALSE
is.integer0(numeric(0)) #FALSE

You can also use assertive for this.

library(assertive)
x <- integer(0)
assert_is_integer(x)
assert_is_empty(x)
x <- 0L
assert_is_integer(x)
assert_is_empty(x)
## Error: is_empty : x has length 1, not 0.
x <- numeric(0)
assert_is_integer(x)
assert_is_empty(x)
## Error: is_integer : x is not of class 'integer'; it has class 'numeric'.

Solution 3

Maybe off-topic, but R features two nice, fast and empty-aware functions for reducing logical vectors -- any and all:

if(any(x=='dolphin')) stop("Told you, no mammals!")

Solution 4

Inspired by Andrie's answer, you could use identical and avoid any attribute problems by using the fact that it is the empty set of that class of object and combine it with an element of that class:

attr(a, "foo") <- "bar"

identical(1L, c(a, 1L))
#> [1] TRUE

Or more generally:

is.empty <- function(x, mode = NULL){
    if (is.null(mode)) mode <- class(x)
    identical(vector(mode, 1), c(x, vector(class(x), 1)))
}

b <- numeric(0)

is.empty(a)
#> [1] TRUE
is.empty(a,"numeric")
#> [1] FALSE
is.empty(b)
#> [1] TRUE
is.empty(b,"integer")
#> [1] FALSE

Solution 5

if ( length(a <- which(1:3 == 5) ) ) print(a)  else print("nothing returned for 'a'") 
#[1] "nothing returned for 'a'"

On second thought I think any is more beautiful than length(.):

 if ( any(a <- which(1:3 == 5) ) ) print(a)  else print("nothing returned for 'a'") 
 if ( any(a <- 1:3 == 5 ) ) print(a)  else print("nothing returned for 'a'") 
Share:
137,532

Related videos on Youtube

Roman Luštrik
Author by

Roman Luštrik

I'm an analyst with roots in veterinary medicine, biology/ecology and biostatistics. I work with data from various fields of natural (genetics, ecology, biotechnology...) and social sciences (e.g. official statistics, economy). Having fun with cloud solutions like AWS. My tool of choice is R, but I can also somewhat handle Python, HTML, CSS. Ask me about reproducible research and version control. I feed many, many cats.

Updated on January 18, 2021

Comments

  • Roman Luštrik
    Roman Luštrik over 3 years

    Let's say we have a statement that produces integer(0), e.g.

     a <- which(1:3 == 5)
    

    What is the safest way of catching this?

    • mbq
      mbq almost 13 years
      I don't like the idea of treating it as an error -- in fact R's policy of not collapsing certain empty objects helps to avoid many error-recover flows, and thus leads to much cleaner code.
    • hadley
      hadley almost 13 years
      Don't use which.
    • IRTFM
      IRTFM almost 10 years
      You can test with any. It will return FALSE for either which(1:3==5) or for 1:3==5 .
    • Roman Luštrik
      Roman Luštrik almost 10 years
      @BondedDust I was trying to find integer(0), which I produced using which as an example.
    • Cactus
      Cactus over 6 years
      I know this is old, but could you, hadley, please outline why not to use which? This would be very helpful for me to avoid bad code.
    • sindri_baldur
      sindri_baldur about 6 years
      Maybe because it can introduce bugs and often not necessary see discussion at the bottom of this page.
  • James
    James almost 13 years
    You could just use !length(x) rather than length(x)==0
  • Richie Cotton
    Richie Cotton almost 13 years
    @James. True, but I don't think there's much of a performance issue either way, and length(x) == 0L reads more clearly to me.
  • eenblam
    eenblam almost 11 years
    @RichieCotton. What's up with 0L as opposed to 0? I've tried googling it, but I'm not finding anything relevant. Sorry about the necromancy.
  • Richie Cotton
    Richie Cotton over 10 years
    @Ben: Adding an L suffix to a number makes R store it as an integer rather than a floating point value. See, e.g., cran.r-project.org/doc/manuals/R-lang.html#Constants
  • Ufos
    Ufos over 6 years
    Yeah, would be great if there was something like is.empty, cuz some functions return integer(0) instead of NA or NULL. But for now your way is the most straightforward, and works vector-wise which is a big advantage over length(a).
  • Andrii
    Andrii about 6 years
    Thanks! It's saved my time.
  • JASC
    JASC over 4 years
    This is not the simplest answer, but by far the simplest and safest for beginners.
  • tjebo
    tjebo over 3 years
    Well .. S4Vectors is an extra package, and one that is (as of today) not on CRAN
  • tjebo
    tjebo over 3 years
    It may be worth to point out to the future reader that length(NULL) == 0 is also TRUE. user E Nord's answer would be an option to test for integer(0) only