// median-gamma.c       Section: 2.8  Median Filter
//      Copyright 1994, Center for Computer Vision and Visualization,
//      University of Florida.  All rights reserved.
// Support file for the iac++ implementation of a median filter,
//      utilizing neighborhood operations.
//

#include "ia.h"
#include "median-gamma.h"


///////////////////////////////////////////////////////////////////
// median_gamma<T>()
//    Calculate the median value from an array of values


template <class T>
T
median_gamma( T *values, unsigned int arraySize ) {

    if (arraySize == 0) {
	// This is very bad, because we do not have a default
	//   value to return, or even a resonable guess.
	// So we\'ll issue an error, and return 0 if we
	//   continue from here.
	ia_throw(IA::INVALID_OPERATION, __FILE__, __LINE__ );
	return T(0);
    }

    // We can calculate the median of N items by sorting
    // the array and returning the middle value if odd,
    // otherwise return the average of the middle two values.

    // We could use a quick-sort, but I\'ll use bubble sort
    // for now.

    int midpt = arraySize / 2;
    for( int i=0; i<=midpt; i++ ) { // enough if even or odd
	for( int j=i+1; j<=arraySize; j++ ) {
	    if (values[i] > values[j]) {
		T tmp = values[i];
		values[i] = values[j];
		values[j] = tmp;
	    }
	}
    }

    // Even or odd ?
    // Of course, this assumes that type T supports both
    //   additon (+) and division (/)....
    if (arraySize % 2) {
	// Odd arraySize, so return the middle value
	return values[ midpt ];
    } else {
	// Even arraySize, so return average
	return (values[midpt-1] + values[midpt]) / 2;
    }
}


