#ifndef FUNCTAB_SEEN
#define FUNCTAB_SEEN

#include "machdefs.h"
#include "tvector.h"
#include "tarray.h"

namespace SOPHYA {

class FuncTab {
public:
  FuncTab(double (*func)(double const),uint_4 nbin,r_8 xmin,r_8 xmax);
  virtual ~FuncTab(void);

  //! Give values for the index [0] and [NTab+1]
  void SetLimVal(void);
  void SetLimVal(r_8 val0,r_8 valn);

  //! Interpolation type
  void SetInterp(uint_2 typ=0);

  //! L'index de la valeur tabulee la plus proche de x (entre 1 et NTab)
  inline uint_4 IndexNear(r_8 x)
    {uint_4 i=(uint_4)((x-XMin)/Dx+0.5) +1; return (i>NTab)? NTab: i;}
  //! L'index de la valeur tabulee juste inferieure a x (entre 1 et NTab)
  inline uint_4 IndexLow(r_8 x)
    {uint_4 i=(uint_4)((x-XMin)/Dx) +1; return (i>NTab)? NTab: i;}

  //! L'abscisse pour la valeur i de l'index
  inline r_8 X(uint_4 i) {return XMin+(i-1)*Dx;}

  //! Le valeur tabulee la plus proche de x
  inline r_8 Value(r_8 x) {return Tabul[IndexNear(x)];}

  //! L'interpolation lineaire dans le bin (attention no-protection for time saving)
  inline r_8 ValueL(r_8 x)
    {uint_4 i=IndexLow(x);
     return Tabul[i]+PInterpL[i]*(x-X(i));}

  //! L'interpolation parabolique (attention no-protection for time saving)
  inline r_8 ValueP(r_8 x)
  {uint_4 i=IndexLow(x); x -= X(i);
     return Tabul[i]+PInterpP[0][i]*x*x+PInterpP[1][i]*x;}

protected:
  double (*Func)(double const);
  uint_4 NTab;
  r_8 XMin,XMax,Dx;
  r_8 *Tabul;
  r_8 *PInterpL;
  r_8 *PInterpP[2];
};

} // Fin du namespace

#endif
