9

Is there a way to distinguish between 1 and c(1)? Apparently in R

c(1) == 1 # TRUE
as.matrix(c(1)) == 1 # TRUE
as.array(c(1)) == 1 # TRUE

which is a problem, for example, if I'm converting a vector to JSON:

library(rjson)
toJSON(c(1,2)) # "[1,2]"
toJSON(c(1)) # "1" instead of "[1]"

Any ideas?

nachocab
  • 13,328
  • 21
  • 91
  • 149

3 Answers3

6

No. As far as I know, there's no difference between 1 and c(1)

> identical(1, c(1))
[1] TRUE

The reason rjson::toJSON returns a different value for c(1) than it does for c(1,2) is because it checks the length and returns differently for length 1 objects

GSee
  • 48,880
  • 13
  • 125
  • 145
6

It works as expected if you pass a list:

> toJSON(list(1))
[1] "[1]"

You can convert with as.list:

> toJSON(as.list(c(1)))
[1] "[1]"
> toJSON(as.list(c(1, 2)))
[1] "[1,2]"

As noted in the other answers, there is no distinction between an atomic value and a vector of length one in R -- unlike with lists, which always have a length and can contain arbitrary objects, not necessarily of the same type.

krlmlr
  • 25,056
  • 14
  • 120
  • 217
1

In R numbers are just vectors of one entry. There is no distinction.

In fact, a one-element vector is automatically printed as if it were just a scalar:

a<- 1
str(a)          # num 1
b<-c(1)
str(b)          # num 1

If your output should encode them differently then you will have to do that manually, which you can do because your program is generating both, it knows which are "real" vectors vs. vectors that have 1 element but are conceptually scalar.

Bernd Elkemann
  • 23,242
  • 4
  • 37
  • 66