rregressionequality

Regression models with same fitted values that output FALSE when compared to each other with equal operator in r


Given the cuadratic models for the odor dataset from the faraway package:

> lmod <- lm(odor ~ I(temp) + I(gas) + I(pack)+I(temp^2)+I(gas^2)+I(pack^2)+I(temp*gas)+I(gas*pack)+I(pack*temp),odor)
> lmod6 <- lm(odor ~ polym(temp,gas,pack,degree = 2),odor)

Both models have the same fitted values:

> lmod$fitted
        1         2         3         4         5         6         7         8         9        10        11        12 
 86.62500  45.87500  36.12500  28.37500  42.50000  15.25000  -3.25000 -24.50000  59.87500  29.37500  20.62500 -16.87500 
       13        14        15 
-30.66667 -30.66667 -30.66667 
> lmod6$fitted
        1         2         3         4         5         6         7         8         9        10        11        12 
 86.62500  45.87500  36.12500  28.37500  42.50000  15.25000  -3.25000 -24.50000  59.87500  29.37500  20.62500 -16.87500 
       13        14        15 
-30.66667 -30.66667 -30.66667 

However, when comparing these fitted values to each other they are not identical, why is that?

> table(lmod6$fitted==lmod$fitted)

FALSE  TRUE 
   13     2 

Solution

  • This is a classic example of the floating point trap as described in chapter 1 of R Inferno by Patric Burns or R FAQ

    The differences are zero up to floating point accuracy:

    options(digits=20)
    lmod$fitted - lmod6$fitted
                            1                          2
     0.0000000000000000000e+00  0.0000000000000000000e+00
                             3                          4
     7.1054273576010018587e-15  1.0658141036401502788e-14
                             5                          6
    -7.1054273576010018587e-15 -3.5527136788005009294e-15
                             7                          8
     4.4408920985006261617e-16 -3.5527136788005009294e-15
                             9                         10
    -1.4210854715202003717e-14 -1.4210854715202003717e-14
                            11                         12
     7.1054273576010018587e-15  3.5527136788005009294e-15
                            13                         14
     7.1054273576010018587e-15  7.1054273576010018587e-15
                            15
     7.1054273576010018587e-15
    

    all.equal() function is designed for testing if the two vectors are "almost equal" (up to fp accuracy):

    all.equal(lmod$fitted,lmod6$fitted)
    [1] TRUE