#ifndef Morpheo_Max_h
#define Morpheo_Max_h

/*
 * $Id: Max.h 88 2008-12-10 18:31:39Z rosiere $
 *
 * [ Description ]
 * 
 */

#include <stdint.h>

namespace morpheo {

  template<typename T> inline T max (T * x, uint32_t size)
  {
    T res = x[0];

    for (uint32_t i=1; i<size; i++)
      {
	T tmp = x[i];
	if (res<tmp)
	  res = tmp;
      }

    return res;
  }

  template<typename T> inline T max (T ** x, uint32_t size1, uint32_t size2)
  {
    T res = max(x[0],size2);

    for (uint32_t i=1; i<size1; i++)
      {
	T tmp = max(x[i],size2);
	if (res<tmp)
	  res = tmp;
      }

    return res;
  }

  template<typename T> inline T max (T ** x, uint32_t size1, uint32_t * size2)
  {
    T res = max(x[0],size2[0]);

    for (uint32_t i=1; i<size1; i++)
      {
	T tmp = max(x[i],size2[i]);
	if (res<tmp)
	  res = tmp;
      }

    return res;
  }


  template<typename T> inline T max (T * x, uint32_t size, uint32_t n)
  {
    if ((n==0) or (n>size))
      return max<T>(x,size);

    // validity array
    bool val [size];
    for (uint32_t i=0; i<size; i++)
      val [i] = true;

    // find min
    T min = x[0];

    for (uint32_t i=1; i<size; i++)
      if (min>x[i])
	min = x[i];
    
    // find n max
    T res = min;
    for (uint32_t i=0; i<n; i++)
      {

	uint32_t index = 0;
	res = min; // always take the minor
	for (uint32_t j=0; j<size; j++)
	  if ((res<x[j]) and val[j]) // find greater value, and slot is valid
	    {
	      res   = x[j];
	      index = j;
	    }
	val [index] = false; // invalid this value
      }

    return res;
  }

  
}; // end namespace morpheo              

#endif
