0

Let's say I have a float called foo. And foo increases or decreases at certain intervals. How can I make foo start from zero again once it succeeded a specified number / and the same in reverse for the decreasing?

For example:

int max = 0;
int min = 50;
float foo = 45;
foo += 7.5;

foo would be 52.5 now. But since I specified 50 at the max number, i want it to sort of overflow at that point so that the result is just 2.5.

Or:

int min = 0;
int max = 50;
float foo = 45;
foo += 108.3;

the result should be 3.3. It just overflowed 3 times.

And for the reverse:

int min = 0;
int max = 50;
float foo = 1;
foo -= 5.5;

the result would be -4.5 but it should be 44.5.

I was thinking that maybe something like this would solve the problem:

foo = foo % max;
if (foo <0)
    foo+=max;

But % is only for integers and including a library just to get fmod feels overkill.

Anyway, I'm wondering if this would work, if it could be done with less code and if it could be done without fmod.

Forivin
  • 14,780
  • 27
  • 106
  • 199
  • 3
    You can use `fmod` for floating point modulo operations – Jens Munk Aug 18 '16 at 10:22
  • 1
    Sorry, didn't read the last line. You can implement a new type and overload all operators, but if you need the functions from `math.h` it is a lot of work. Alternatively, implement your own fmod – Jens Munk Aug 18 '16 at 10:25
  • 1
    `without fmod` Why don't use it? – ikh Aug 18 '16 at 10:31
  • `[...] including a library just to get fmod feels overkill.` – Forivin Aug 18 '16 at 10:33
  • 2
    @Forivin `fmod` is part of the standard library, which means your program will contain it whether you use it or not. So why not use it? – Angew is no longer proud of SO Aug 18 '16 at 10:34
  • But why do I have to use `#include ` in order to use it? – Forivin Aug 18 '16 at 10:37
  • 1
    *"But why do I have to use `#include ` in order to use it?"* - Because symbols have to be declared, before they can be used. A feature of just about any single-pass compiler. That's C++ 101, really. Maybe you should visit [The Definitive C++ Book Guide and List](http://stackoverflow.com/q/388242/1889329) and get some of those. – IInspectable Aug 18 '16 at 16:00

4 Answers4

2

Because #include <fmod> is too mainstream you can use;

if(foo > max)
{
   int c = foo / max; 
   foo = foo - max*c;
}
else if(foo < min)
{
    int c  = foo / max;
    if( c < 0 ) c = c * -1;
    foo = foo + max*c;
    foo = max + foo;
}

results:

for:

int min = 0;
int max = 50;
float foo = 1;
foo -= 5.5;

cpp.sh/4akud

for:

int min= 0;
int max= 50;
float foo = 45;
foo += 7.5;

cpp.sh/3accv

mucisk
  • 247
  • 5
  • 13
1

including a library just to get fmod feels overkill.

How so ? If you don't use the other functions, they won't lead to any overhead, and the increase in compiling time from including cmath surely is negligeable.

Just use the standard library unless you have a good reason not to.

You might want to read that : Are unnecessary include files an overhead?

Community
  • 1
  • 1
Nelfeal
  • 12,593
  • 1
  • 20
  • 39
  • I'm just worried because my target system only has 2000 bytes of RAM. – Forivin Aug 18 '16 at 10:47
  • @Forivin: 2 KiB of RAM sounds like very little, even for an embedded system. If that is really all you have, it's something that needs to be in your question. – IInspectable Aug 18 '16 at 16:03
  • @Forivin: including a header doesn't use any additional ram whatsoever. However, _writing your own function instead of using the library might_. Often, the compiler knows the standard library functions, and converts those to a single operation. If you write your own, it can't do that. – Mooing Duck Aug 18 '16 at 23:07
0
const float TOP_CAP = 5.0f;
const float LOW_CAP = 1.0f;

float value = 42.0f;
while(value >= CAP)
{
    value -= TOP_CAP;
    while(value < LOW_CAP)
        value += LOW_CAP;
}
while(value < LOW_CAP)
        value += LOW_CAP;

If a whiles condition is false then the loop will be skipped.

Or just #include math and use fmod.

Ivan Rubinson
  • 3,001
  • 4
  • 19
  • 48
  • While the use of `while` seems the most simplistic solution, your code does not do what the question asked. Especially it will not result in a modulo something arithmetic, as you have two increments. – Lutz Lehmann Aug 18 '16 at 22:51
0

Concurring with Ivan Rubinson the use of single increments and decrements inside while loops seems the most simplistic solution to the problem, especially if one can expect values only shortly outside the interval.

int min = 0;
int max = 50;
int mod = max - min;
float foo = 45;
foo += 7.5;

while(foo >= max) foo -= mod;
while(foo <  min) foo += mod;
Lutz Lehmann
  • 25,219
  • 2
  • 22
  • 51