Dear R People: I am getting some odd results when using logical operators:> x <- seq(from=-1,to=1,by=0.1)> > x[1] -1.0 -0.9 -0.8 -0.7 -0.6 -0.5 -0.4 -0.3 -0.2 -0.1 0.0 0.1 0.2 0.3 0.4 [16] 0.5 0.6 0.7 0.8 0.9 1.0> x == -1[1] TRUE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE [13] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE> x == -0.9[1] FALSE TRUE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE [13] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE> x == -0.8[1] FALSE FALSE TRUE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE [13] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE> x == -0.7[1] FALSE FALSE FALSE TRUE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE [13] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE> x == -0.6[1] FALSE FALSE FALSE FALSE TRUE FALSE FALSE FALSE FALSE FALSE FALSE FALSE [13] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE> x == -0.5[1] FALSE FALSE FALSE FALSE FALSE TRUE FALSE FALSE FALSE FALSE FALSE FALSE [13] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE> x == -0.4[1] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE [13] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE>Should this show as true also, please? I saw this in both Windows and LINUX Versions 2.4.0 Thanks in advance, Sincerely, Erin Hodgess Associate Professor Department of Computer and Mathematical Sciences University of Houston - Downtown mailto: hodgess at gator.uhd.edu
Erin Hodgess wrote:> Dear R People: > > I am getting some odd results when using logical operators: > >> x <- seq(from=-1,to=1,by=0.1) > >>> x > [1] -1.0 -0.9 -0.8 -0.7 -0.6 -0.5 -0.4 -0.3 -0.2 -0.1 0.0 0.1 0.2 0.3 0.4 > [16] 0.5 0.6 0.7 0.8 0.9 1.0 >> x == -1 > [1] TRUE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE > [13] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE >> x == -0.9 > [1] FALSE TRUE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE > [13] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE >> x == -0.8 > [1] FALSE FALSE TRUE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE > [13] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE >> x == -0.7 > [1] FALSE FALSE FALSE TRUE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE > [13] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE >> x == -0.6 > [1] FALSE FALSE FALSE FALSE TRUE FALSE FALSE FALSE FALSE FALSE FALSE FALSE > [13] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE >> x == -0.5 > [1] FALSE FALSE FALSE FALSE FALSE TRUE FALSE FALSE FALSE FALSE FALSE FALSE > [13] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE >> x == -0.4 > [1] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE > [13] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE > > Should this show as true also, please?They are not exactly equal. You could use all.equal() to test for nearly equal.> x[7] == -0.4[1] FALSE> all.equal(x[7], -0.4)[1] TRUE> all.equal(x[7], -0.4, tol = 0)[1] "Mean relative difference: 2.775558e-16"> I saw this in both Windows and LINUX Versions 2.4.0 > > Thanks in advance, > Sincerely, > Erin Hodgess > Associate Professor > Department of Computer and Mathematical Sciences > University of Houston - Downtown > mailto: hodgess at gator.uhd.edu > > ______________________________________________ > R-help at stat.math.ethz.ch mailing list > https://stat.ethz.ch/mailman/listinfo/r-help > PLEASE do read the posting guide http://www.R-project.org/posting-guide.html > and provide commented, minimal, self-contained, reproducible code.-- Chuck Cleland, Ph.D. NDRI, Inc. 71 West 23rd Street, 8th floor New York, NY 10010 tel: (212) 845-4495 (Tu, Th) tel: (732) 512-0171 (M, W, F) fax: (917) 438-0894
This is FAQ 7.31 in the R FAQ. Basically computers in general have problems exactly representing all but a few floating point numbers, so while 2 numbers may look the same when displayed (rounded to a couple of digits), they are different if you look at them in full precision due to different roundings. Functions like all.equal deal with this by checking to see if numbers are close enough rather than equal. The general rule is to not expect exact equality between floating point numbers. This is a problem for computers in general, not just R. Hope this helps, -- Gregory (Greg) L. Snow Ph.D. Statistical Data Center Intermountain Healthcare greg.snow at intermountainmail.org (801) 408-8111 -----Original Message----- From: r-help-bounces at stat.math.ethz.ch [mailto:r-help-bounces at stat.math.ethz.ch] On Behalf Of Erin Hodgess Sent: Friday, December 29, 2006 3:36 AM To: r-help at stat.math.ethz.ch Subject: [R] strange logical results Dear R People: I am getting some odd results when using logical operators:> x <- seq(from=-1,to=1,by=0.1)> > x[1] -1.0 -0.9 -0.8 -0.7 -0.6 -0.5 -0.4 -0.3 -0.2 -0.1 0.0 0.1 0.2 0.3 0.4 [16] 0.5 0.6 0.7 0.8 0.9 1.0> x == -1[1] TRUE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE [13] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE> x == -0.9[1] FALSE TRUE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE [13] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE> x == -0.8[1] FALSE FALSE TRUE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE [13] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE> x == -0.7[1] FALSE FALSE FALSE TRUE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE [13] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE> x == -0.6[1] FALSE FALSE FALSE FALSE TRUE FALSE FALSE FALSE FALSE FALSE FALSE FALSE [13] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE> x == -0.5[1] FALSE FALSE FALSE FALSE FALSE TRUE FALSE FALSE FALSE FALSE FALSE FALSE [13] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE> x == -0.4[1] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE [13] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE>Should this show as true also, please? I saw this in both Windows and LINUX Versions 2.4.0 Thanks in advance, Sincerely, Erin Hodgess Associate Professor Department of Computer and Mathematical Sciences University of Houston - Downtown mailto: hodgess at gator.uhd.edu ______________________________________________ R-help at stat.math.ethz.ch mailing list https://stat.ethz.ch/mailman/listinfo/r-help PLEASE do read the posting guide http://www.R-project.org/posting-guide.html and provide commented, minimal, self-contained, reproducible code.
Hi Erin, You would be safe on a machine that represented floating point numbers in base 10, and I haven't seen one of those for such a long time... All modern machines use base 2 for floating point numbers. The moral of the story is not to believe what you see printed. The number you see printed innocently as '-0.4' has been arrived at by two different processes and uses two different *approximations* to the real thing on a binary machine, and my chance they have arrived at a slightly different result. Slight, but enough to make '==' ring the alarm. Here is a demo.> x <- seq(-1,1,by=0.1) > x[7] - (-0.4)[1] 1.110223e-16 So the method used by seq() to arrive at an approximation to -0.4 is just slightly different from the method used by the parser when it reads the characters '-0.4' and translates them into a floating point number. It just so happens that for the others you checked the two approximations agreed, but you can't trust that to happen all the time. Moral of the story: don't use the '==' or '!=' operators with floating point numbers. It's an old tale but still current. OK, so what can you do to implement the idea of checking equality 'within a tolerance'? I'm glad you asked. You can write a couple of binary operators yourself. There is an object called .Machine that is a list of machine constants. The obvious one to compare the difference with is .Machine$double.eps> `%~=%` <- function(a, b) abs(a - b) < .Machine$double.eps > `%~!%` <- function(a, b) abs(a - b) > .Machine$double.eps > x %~=% -0.4[1] FALSE FALSE FALSE FALSE FALSE FALSE TRUE FALSE FALSE FALSE FALSE FALSE FALSE FALSE [15] FALSE FALSE FALSE FALSE FALSE FALSE FALSE> x %~!% -0.4[1] TRUE TRUE TRUE TRUE TRUE TRUE FALSE TRUE TRUE TRUE TRUE TRUE TRUE TRUE [15] TRUE TRUE TRUE TRUE TRUE TRUE TRUE The world is approximately sane once more. Bill Venables. -----Original Message----- From: r-help-bounces at stat.math.ethz.ch [mailto:r-help-bounces at stat.math.ethz.ch] On Behalf Of Erin Hodgess Sent: Friday, 29 December 2006 8:36 PM To: r-help at stat.math.ethz.ch Subject: [R] strange logical results Dear R People: I am getting some odd results when using logical operators:> x <- seq(from=-1,to=1,by=0.1)> > x[1] -1.0 -0.9 -0.8 -0.7 -0.6 -0.5 -0.4 -0.3 -0.2 -0.1 0.0 0.1 0.2 0.3 0.4 [16] 0.5 0.6 0.7 0.8 0.9 1.0> x == -1[1] TRUE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE [13] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE> x == -0.9[1] FALSE TRUE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE [13] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE> x == -0.8[1] FALSE FALSE TRUE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE [13] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE> x == -0.7[1] FALSE FALSE FALSE TRUE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE [13] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE> x == -0.6[1] FALSE FALSE FALSE FALSE TRUE FALSE FALSE FALSE FALSE FALSE FALSE FALSE [13] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE> x == -0.5[1] FALSE FALSE FALSE FALSE FALSE TRUE FALSE FALSE FALSE FALSE FALSE FALSE [13] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE> x == -0.4[1] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE [13] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE>Should this show as true also, please? I saw this in both Windows and LINUX Versions 2.4.0 Thanks in advance, Sincerely, Erin Hodgess Associate Professor Department of Computer and Mathematical Sciences University of Houston - Downtown mailto: hodgess at gator.uhd.edu ______________________________________________ R-help at stat.math.ethz.ch mailing list https://stat.ethz.ch/mailman/listinfo/r-help PLEASE do read the posting guide http://www.R-project.org/posting-guide.html and provide commented, minimal, self-contained, reproducible code.