Making an array Fails for mysterious reason (small stepsize)

1 view (last 30 days)
In short:
fs = 50000;
x1 = (0:1/fs:1);
find(x1==0.5)
This works fine. The value of 0.5 is found in the array.
fs = 50000;
x2 = ( 0:1/fs:(1-1/fs) );
find(x2==0.5)
Does not work. The value of 0.5 is not there anymore and the find-function returns an empty matrix. I would have expected that x2 would be the equivalent of x1(1:end-1) but that does not seem to be the case. For smaller values fs (e.g. 5000) everything is fine. Can someone tell me what is going on exactly?
Thanks

Accepted Answer

Stephen23
Stephen23 on 21 Sep 2016
Edited: Stephen23 on 21 Sep 2016
"I would have expected that x2 would be the equivalent of x1(1:end-1)"
Nope. Those two values include floating point error and are calculated from different end values. Read this:
Quoting that answer:
"To counteract such error accumulation, the algorithm of the COLON operator dictates that:
1. The first half of the output vector (in this example ‘v’) is calculated by adding integer multiples of the step ‘d’ to the left-hand endpoint ‘a’.
2. The second half is calculated by subtracting multiples of the step ‘d’ from the right-hand endpoint."
For your values, we can see that the first vector contains:
>> fs = 50000;
>> x1 = 0:1/fs:1;
>> sprintf('%.30f',x1(25001))
ans =
0.500000000000000000000000000000
but the second vector contains:
>> x2 = 0:1/fs:(1-1/fs);
>> sprintf('%.30f',x2(25001))
ans =
0.499999999999999940000000000000
This is, according the above explanation, because the lengths of the two vectors are different and the "0.5" value is therefore calculated from different end values. This is easy to calculate ourselves, based on the explanation above. From the left-hand end for the first vector:
>> sprintf('%.30f',0+25000*(1/fs))
ans =
0.500000000000000000000000000000
and from the right-hand end for the second vector:
>> sprintf('%.30f',(1-1/fs)-24999*(1/fs))
ans =
0.499999999999999940000000000000
which matches exactly the values that you are getting.
Of course comparing floating point numbers for equality is never a good idea: always use a tolerance:
If you really want to see what the floating point values really are, try this:

More Answers (1)

KSSV
KSSV on 21 Sep 2016
It is not advised to compare floating point numbers using ==. You have to fix a small number (tolerance) say, eps = 10^-5 and check for is the absolute difference less then that. If so then the floating point numbers are close enough. '
More on:
  1 Comment
Stephen23
Stephen23 on 21 Sep 2016
Edited: Stephen23 on 21 Sep 2016
@Dr. Siva Srinivas Kolukula: sure, but this does not answer the question of why the two sequences are different. See my answer for the reason.

Sign in to comment.

Categories

Find more on Multidimensional Arrays in Help Center and File Exchange

Tags

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!