Take the 2-minute tour ×

Sorry, this is nothing about image, I just don't know how to ask the question properly.

My question is, I am writing a C++ code, and doing a calculation.


b is varying with time from zero to its amplitude, say bmax. (actually, b=bmax*sin(t).)

However, I found when b is very small, the result a is gradually deviating from my analytic results.

So I am wondering how to keep a very high resolution of the results, to avoid the cut-off of the floating points.

share|improve this question
Gradually deviating how, specifically? In terms of absolute error? Relative error? How are you calculating your reference? –  Oliver Charlesworth Nov 10 '11 at 16:15
Also, is the fact that it's cos(c) irrelevant? For the purposes of this question, can we replace cos(c) with k? –  Oliver Charlesworth Nov 10 '11 at 16:15
Are you using floats or doubles? –  GazTheDestroyer Nov 10 '11 at 16:19
I apologize, that this is not a well posted question. I just can't diagonoze where the problem is. You can see from the following video, youtu.be/n9bOEr0IAB4 –  Daniel Nov 10 '11 at 16:36
As you can see, this is a CFD simulation, mesh movement, move the mesh point from a rec shape to a round corner shape, but after running, I found it is not round any more, not knowing where the problem is. The mesh points coordinates are just simply function or b*cos(c). Where b is the round corner radius, and c is the mesh points' angles. The radius b is gradually changing with time. So at certain time, b value would be very small. I am not sure whether this is the problem or not. –  Daniel Nov 10 '11 at 16:40

2 Answers 2

up vote 3 down vote accepted

When you say it's gradually deviating it sounds like you've got an accumulation of error there (although there's nothing obvious in the code you posted). For example this code the error accumulates with every iteration around the while loop:

#include <iostream>

int main() {
  unsigned short counter;
  float val = 0;
  while (counter++) {
    val += 0.001f;
    std::cout << val << "\n";

Where as re-writing it like:

#include <iostream>

int main() {
  unsigned short counter;
  while (counter++) {
    float val = counter * 0.001f;

does not cause this accumulation of error as val only depends upon the integer (which is exactly representable) and not the previous values of val each of which will have introduced some small error.

share|improve this answer
Thank you. Since the mesh points movements is calculated in this way, so I don;t think this is an accumulation error.... The way is, say A is the olf position, B is the new postion, B is calculated from the target function, which should have been precise position. So at each time the current position is simply "A+(B-A)". So my understanding is that it is related to the B' precision. That's the reason I asked. –  Daniel Nov 10 '11 at 16:46
If A is the old position and B is the new position and you use A (or B before it's changed) in the calculation of the new position then you will have exactly this kind of error. –  Flexo Nov 10 '11 at 16:48
Thank you so much, what if I have to do in the first way, is there an another solution? I am working on a code, which I currently can do nothing about its basis classes, which mean, so far, my best way to do it is to provide the (B-A) value, that is the change of position each timestep Delta=B-A. I understand from your answer, that I should work my best to avoid an addition or a subtraction operation between a small number and another small number. But so far I have no choice. :( –  Daniel Nov 10 '11 at 17:01
I hope there could be a temporarily a high precision function, so that I could work in this way, like a=highPre(b)*cos(c). –  Daniel Nov 10 '11 at 17:03
If you can express your position as a sum of "deltas" You might be able to use Kahan summation to reduce the error. –  Flexo Nov 10 '11 at 17:07

Another idea is to keep the values in integral units as much as possible. Only convert when necessary.


unsigned long value;
const unsigned long scale_factor = 1E6;

// Cosine returns floating point, so convert it to fixed point.
unsigned long temp = cos(c) * scale_factor;

// Reduce propagation of floating point error, by using integral arithmetic.
value = value * temp;
value *= b;

Another alternative is to have your own lookup or interpolation tables for when the delta is very small.

share|improve this answer

Your Answer


