//**********************************************************************
//**********************************************************************
//	Projet      : Ulysse
//	Laboratoire : GREYC-ISMRA
//	Fichier     : assoc.cc
//      Annee       : 1997          ,
//	Auteur      : Christophe GODEREAUX
//**********************************************************************
//**********************************************************************

#ifndef ASSOCCCC
#define ASSOCCCC



#include <string.h>

//**********************************************************************
//		Tableau associatif chaine -> chaine
//**********************************************************************

#define NB_ENTREE 7
#define CHAINE_NOM 20
#define CHAINE_VALEUR 30

struct pair_chaine {
	  char nom[CHAINE_NOM];
	  char val[CHAINE_VALEUR];
  };

class assoc_chaine {

  int free;

//  assoc_chaine(const assoc_chaine&);
//  assoc_chaine& operator=(const assoc_chaine&);
  public:
  pair_chaine vec[NB_ENTREE];
  int val_free(){return free;}
  assoc_chaine();
  void ajouter(char*n,char*v);
  char* operator[](const char* p);
};
  
  
assoc_chaine::assoc_chaine()
{ 
  free=0;
}

void assoc_chaine::ajouter(char*n,char*v)
{
  if (free==NB_ENTREE) 
    cerr<<"Tableau associatif chaine trop d'entree, modifier NB_ENTREE";
  else {
    strcpy(vec[free].nom,n);
    strcpy(vec[free++].val,v);
  }
}

char* assoc_chaine::operator[](const char* p)
{
  register pair_chaine* pp;
  for (pp=&vec[free-1]; vec<=pp; pp--)
    if (strcmp(p,pp->nom)==0) 
      return pp->val;
  cerr<<"le champs de nom :"<<p<<" n'existe pas !!!!!";cerr.flush();
  return NULL;
}


ostream& operator<<(ostream& s,  assoc_chaine a)
{
  if (a.val_free()!=0){
    s<<"  Champs :\n    ";
    for (int i=0; i<a.val_free();i++)
      s<<a.vec[i].nom<<"="<<a.vec[i].val<<"  ";
    return s<<'\n';
  }
  return s;
}




//**********************************************************************
//		Tableau associatif compteur avec Patron
//**********************************************************************

struct pair {
	  char *name;
	  int val;
  };

template<class T> class assoc {


  T* vec;
  int max;
  int free;

  assoc(const assoc&);
  assoc& operator=(const assoc&);

  public:
  
    assoc(int s)
{
  max=(s<16) ?16 : s;
deb("max=");debn(max);
  free=0;
  vec = new T[max];
}

    int& operator[](const char* p)
{
  register T* pp;
  for (pp=&vec[free-1]; vec<=pp; pp--)
    if (strcmp(p,pp->name)==0) return pp->val;

  if (free==max) {
    T* nvec =new T[max*2];
    for (int i=0; i<max;i++) nvec[i] =vec[i];
    delete vec;
    vec=nvec;
    max = 2*max;
  }
  pp=&vec[free++];
  pp->name=new char[strlen(p)+1];
  strcpy(pp->name,p);
  pp->val=0;
  return pp->val;
}


    void print_all()
{
  for (int i=0; i<free;i++)
    cout<<vec[i].name<<": "<<vec[i].val<<"\n";
}


};



//**********************************************************************
//			PATRON Tablo
//**********************************************************************

template<class T> class Tablo {


  T* vec;
  int max;
  int free;

  Tablo(const Tablo&);
  Tablo& operator=(const Tablo&);

  public:
  
    Tablo(int s)
{
  max= s;
  free=0;
  vec = new T[max];
}

    T& operator[](const int i)
{
  return vec[i];
}

    int nbr()
{
  return free;
}

    int ajouter(const T &elem)
{
  if (free==max) {
/*    T* nvec =new T[max*2];
    for (int i=0; i<max;i++) nvec[i] =vec[i];
    delete vec;
    vec=nvec;
    max = 2*max;
    //cout<<"debordement max="<<max<<'\n';
*/ return FALSE; // au cas ou on est au maximum on ne fait rien et
		 // on retourne FALSE
  }
  vec[free++]=elem;
  return TRUE;
}

    void supprimer(const int num)
{
  free--;
  for (int i=num;i<free;i++)vec[i]=vec[i+1];
  T tmp;
  vec[free]=tmp;
}

    void print_all()
{
  for (int i=0; i<free;i++)
    cout<<vec[i]<<'\n';
}
  

};

 
/*
EXEMPLE :

class machin {
      Tablo<int> vec;

public :
   machin():vec(2){}
   void essai(){ vec.ajouter(3);vec.ajouter(4);vec.ajouter(5);}
   void affiche(){vec.print_all();}
};


  machin truc;
  
  truc.essai();
  truc.affiche();
*/


#endif
