Floating point numbers have a bit dedicated to the sign of a number. The round()
function doesn't flip that flag in the case of rounding to 0. You can have a signed zero value when working with floating point numbers.
You can see the hex value representation of the bytes of a number with sprintf
. For example
x <- c(.1,-.1)
sprintf("%a", x)
# [1] "0x1.999999999999ap-4" "-0x1.999999999999ap-4"
sprintf("%a", round(x))
# [1] "0x0p+0" "-0x0p+0"
In this representation the signed bit is indicated with the presences or absence of the "-" in the string. We can see that the rounded version keeps the sign bit the same.
For all intents and purposes, the -0 will act just like a regular 0. You can get rid of the negative by adding 0 to your result.
formatC(round(x)+0)
# [1] "0" "0"
But really this is just happening because you are using the low-level formatC
function. Even R itself doesn't distinguish between 0 and -0 when displaying the numbers. Because R tries to hide this detail, I don't think you can distinguish between the two in R. you'd have to write your own C/C++ code to check the sign digit yourself.
For more non-R specific discussion see: Negative Zero in C