digitalSmooth with quicksort of arrays...

Hello :),

wanted to use the digitalsmooth code from Paul Badger but to make it work faster because I have several sensors to smooth...

The "quicksort" runs good in Processing and cuts down calculationtime and I simply copy and paste it to arduino. Anybody some comments how to improve it for Arduino? Is it allright that way???

Here the updated piece of code:

//smoothing of an array of values
int digiSmooth(int rawIn, int *sensSmoothArray){ // "int *sensSmoothArray" passes an array to the function...
  // *asterisk indicates the array name is a pointer -> Arduino cappable of that???

  /* throw out top and bottom 15% of samples - limit to throw out at least one from top and bottom
   with 15 filtersamples will be 2 and 13 */
  static byte bottom = max( ((filtersamples * 15) / 100), 1 );  //lower border value
  static byte top = min( (((filtersamples  * 85) / 100) + 1), (filtersamples - 1) ); // the +1 is to make up for asymmetry caused by int rounding

  static int sorted[filtersamples]; //static because only needed in this function but persistend throughout the run???

  //////////////////////////////////overwrite last value, shift and put new value in front
  byte i;
  for(i=0; i<filtersamples; i++){
    sorted[i] = sensSmoothArray[i];
  }
  byte j;
  for(j=0; j<filtersamples-1; j++){
    sensSmoothArray[j+1] = sorted[j];
  }
  sensSmoothArray[0] = rawIn; // input new data into the first slot


  //////////////////////////////////sorting
  byte k;
  for (k=0; k<filtersamples; k++){     // transfer data array to local array for sorting and averaging
    sorted[k] = sensSmoothArray[k];
  }

  quicksort(sorted, 0, filtersamples-1);  // quicksort from a elements from x to n elements

  //////////////////////////////////calculating
  byte n = 0; // I think we will not have more than 253
  unsigned long total = 0; //depending on the number of samples this could be a big value

  byte l;
  for (l = bottom; l< top; l++){
    total += sorted[l];  // total remaining indices
    n++; 
  }

  //  Serial.println();
  //  Serial.print("average = ");
  //  Serial.println(total/n);
  return total / n;    // divide by number of samples and return

}


/* replaced by luke through quicksort -> seems to be the fastest to process information on Arduino ??? */
////////////////////////////////////////
void quicksort(int a[], int l, int r){            //a=Array, l=left border, r=right border
  if(r>l){                              //as long that more then 1 followingelement exists do
    int i=l-1, j=r, tmp;                  //Initialising the variables with the borders
    for(;;){                        //endless loop; stops if i>=j
      while(a[++i]<a[r]);                  //inkrem., until found bigger element
      while(a[--j]>a[r] && j>i);            //dekrem., until found smaler element
      if(i>=j) break;                   //stops run if pointer meet
      tmp=a[i];                        //exchange smaller with bigger element
      a[i]=a[j];                       //exchange smaller with bigger element
      a[j]=tmp;                        //exchange smaller with bigger element
    }
    tmp=a[i];           //exchange dividing element
    a[i]=a[r];          //exchange dividing element
    a[r]=tmp;            //exchange dividing element

    quicksort(a, l, i-1);                  //recursive call of function for left
    quicksort(a, i+1, r);                  //recursive call of function for right
  }
}

Thanxs for comments

search on google for a pdf called "An Introduction to the Kalman Filter"

Authors "Greg Welch and Gary Bishop"

There is an incremental way of smoothing that will give you some quick performance

Thanks for the hint. :o

Does anybody know if I can implement this in Arduino directly and if it would make the quicksort execute faster:

/**
    The qsort() function is a modified partition-exchange sort, or
    quicksort.

    The qsort() function sorts an array of \c nmemb objects, the
    initial member of which is pointed to by \c base.  The size of
    each object is specified by \c size.  The contents of the array
    base are sorted in ascending order according to a comparison
    function pointed to by \c compar, which requires two arguments
    pointing to the objects being compared.

    The comparison function must return an integer less than, equal
    to, or greater than zero if the first argument is considered to
    be respectively less than, equal to, or greater than the second.
*/

extern void qsort(void *__base, size_t __nmemb, size_t __size,
             __compar_fn_t __compar);

thanxs