# Another Lesson in Floating Point

In an earlier post I discussed the issue of floating point accuracy in calculations. I have another example to share today that has been lurking in the Mapping Toolbox product. The issue is with the function wrapTo180.

### Work-around

There is a work-around for those of you using Mapping Toolbox with releases R2007b and R2008a.

### Numerical Issue

In R2007b and R2008a, the implementation for wrapTo180 causes results from wrapTo180(lon) to differ very slightly from lon even for for certain values of lon in the interval [-180 180]. The differences are on the order of 2*eps(lon).

### Test Case

The following should evaluate to true.

lon = 115.8323;

but doesn't.

isequal(lon,wrapTo180(lon))
ans =
0


These quantities aren't equal because of the arithmetic being done: 115.8323 + 180 - 180 differs from 115.8323 by

(lon + 180 - 180) - lon
ans =
2.8422e-014


which happens to be

2*eps(lon)
ans =
2.8422e-014


### The Code

Here's the code for wrapTo180

type wrapTo180
function lon = wrapTo180(lon)
%wrapTo180 Wrap angle in degrees to [-180 180]
%
%   lonWrapped = wrapTo180(LON) wraps angles in LON, in degrees, to the
%   interval [-180 180] such that 180 maps to 180 and -180 maps to -180.
%   (In general, odd, positive multiples of 180 map to 180 and odd,
%   negative multiples of 180 map to -180.)
%

% Copyright 2007 The MathWorks, Inc.
% $Revision: 1.1.6.2$  $Date: 2007/08/20 16:35:59$

lon = wrapTo360(lon + 180) - 180;



### Simple Fix

We can just skip the arithmetic operation for values,like 115.8323, that already are in the interval [-180 180]. A nice way to do this is with logical indexing and we can replace the line of code with this.

q = (lon < -180) | (180 < lon);
lon(q) = wrapTo360(lon(q) + 180) - 180;