This discussion has been locked.
You can no longer post new replies to this discussion. If you have a question you can start a new discussion

long long int for floating average computation

I want to compute a floating average of third order.
Just take a look at my code:

void IRQ_Handler()__irq __ram
{
        static long long unsigned int ACC1,ACC2,ACC3,ACC3D;
        static long long unsigned int D1,D2,D3,D1D,D2D;
        static unsigned int int_counter;
        char text[10];

        T0CLRI = 0;
        ADCCON = 0x6A3;                 // software conv., single-ended, conv. enabled
        while (!ADCSTA){}               // wait for end of conversion

        ACC1 += (ADCDAT >> 16) * 100;
        ACC2 += ACC1;
        ACC3 += ACC2;

        if (!(int_counter++ & 0x7F))
        {
                D1 = ACC3 - ACC3D;
                D2 = D1 - D1D;
                D3 = D2 - D2D;
                ACC3D = ACC3;
                D1D = D1;
                D2D = D2;

                sprintf(text,"%8.d",D3 >> 21);
                SDA5708_printf(text);
        }
}


befor i used long long there were overflow.
If increasing Filter lenght there will be overflows even while using long long. Is there a work around?

  • if indeed you have an overflow (I guess here

    ACC1 += (ADCDAT >> 16) * 100;
    

    , why then not store the lower double word separate than the upper double word....?

  • Tamir: Take a closer look at the algorithm. ACC1 is just an ordinary sum.

    ACC2 is a sum of sums, which means it increases quite quicly.

    ACC3 is a sum of sums of sums, which means that it increases very, very fast.

    One thing to look at here is to scale down ACC3 a number of steps, and then scale up D1 after you have computed the difference. You will have to bring up pen and paper and figure out the maximum loss of precision you may get in the final answer - or simulate everything with double and compare with scaled integers.

    Note that ACC1 does not need to use long long, so you might be able to cut a bit of time and code size.

  • i used long long there were overflow.

    With the algorithm as shown, there will always be overflow. It assumes infinitely large integers, which simply don't exist in any CPU. You keep adding non-negative numbers to ADC1 etc., but you never subtract anything. That leaves it no other way to go but through the roof.

    You're also wasting a whole factor of 100 of usable range, for no apparent reason.

    Ultimately, this is the wrong place to ask this. This is purely algorithmic question unrelated to both Keil and ARM.