Back to index

wims  3.65+svn20090927
chemeq.h
Go to the documentation of this file.
00001 // -*- coding: utf-8 -*-
00002 #ifndef CHEMEQ_H
00003 #define CHEMEQ_H
00004 
00005 #include <cstring>
00006 #include <sstream>
00007 #include <iostream>
00008 #include <vector>
00009 #include <string>
00010 #include <map>
00011 
00012 #define VERSION "2.8"
00013 
00014 /* Constante d'Avogadro, recommandée par CODATA, 2006 */
00015 #define Avogadro 6.022141e+23
00016 
00017 /* Charge élémentaire, voir wikipedia, 2007 */
00018 #define Electron 1.602176e-19
00019 
00020 /* Constante de Boltzmann, voir Wikipedia, 2007 */
00021 #define Kb 1.3806e-23
00022 
00023 /* D'où la constante de Faraday */
00024 #define Faraday (Avogadro * Electron)
00025 
00026 /* D'où la constante des Gaz parfaits 8.314 J.K^-1.mol^-1 */
00027 #define R (Kb * Avogadro)
00028 
00029 /* Température de référence pour les réactions chimiques, 25C */
00030 #define T0 (273.15+25)
00031 
00032 /* MINVAL est une valeur impossible tant pour un potentiel standard */
00033 /* que pour une constante d'équilibre                               */
00034 #define MINVAL -999
00035 
00036 typedef struct {
00037   int Zed;
00038   char symb[4];
00039 } atome;
00040 
00041 extern atome lesatomes[];
00042 
00043 typedef std::pair<std::string,int> AtomeCompte;
00044 
00045 class Compteur : public std::map<std::string,float>{
00046 public:
00047   std::ostream & operator << (std::ostream & o)const;
00048 };
00049 
00050 std::ostream & operator << (std::ostream & o, const Compteur & c);
00051 
00052 class Chemeq;
00053 
00054 class fraction{
00055 public:
00056   int i;
00057   int d;
00058   fraction(int numerateur, int denominateur=1):i(numerateur),d(denominateur){};
00059   void inverse(){int n=i; i=d; d=n;};
00060   void simplifie();
00061 };
00062 
00063 const fraction & minFraction(const fraction&, const fraction &);
00064 
00065 std::ostream & operator << (std::ostream & o, fraction f);
00066 
00067 fraction operator * (fraction f, int m);
00068 fraction operator * (int m, fraction f);
00069 fraction operator * (fraction f, fraction m);
00070 fraction operator + (fraction f, fraction g);
00071 fraction operator - (fraction f, fraction g);
00072 
00073 bool operator > (fraction f, int i);
00074 bool operator > (fraction f1, fraction f2);
00075 bool operator != (fraction f, int i);
00076 
00077 class AtomeListe{
00078   AtomeListe * suiv, *group;
00079   char symb[4];
00080   int Zed, nb, no, sqbr;
00081 
00082  public:
00083   AtomeListe(const char* nom, int num, AtomeListe * s=0, AtomeListe * g=0){
00084     strncpy(symb,nom,3); Zed=num; nb=1; sqbr=0;
00085     /* sqbr == 1 quand il y a un square bracket */
00086     suiv = s; group=g;
00087   };
00088   AtomeListe(const AtomeListe & a):
00089     suiv(a.suiv), group(a.group), Zed(a.Zed), nb(a.nb), sqbr(a.sqbr){
00090     strncpy(symb,a.symb,3);
00091   };
00092   const char * symbole() const{return symb;};
00093   int Z()const{return Zed;};
00094   int sq()const{return sqbr;};
00095   void sq(int val){sqbr=val;};
00096   void numerote(int n=0);
00097   void setmolecularite(int n){nb=n;};
00098   int getmolecularite()const{return nb;};
00099   AtomeListe * groupe(){return group;};
00100   void groupe(AtomeListe * al){group= al;};
00101   const AtomeListe * suivant()const{return suiv;};
00102   const AtomeListe * groupe()const{return group;};
00103   void setsuivant(AtomeListe * s){suiv=s;};
00104   void compte (Compteur &c, fraction mult=fraction(1,1))const;
00105   double weight(fraction mult=fraction(1,1))const;
00106   static AtomeListe * triage(AtomeListe * al);
00107   void printcount(std::ostream & o, const fraction&, int multiple) const;
00108   void printnorm(std::ostream & o) const;
00109   bool isEqual(const AtomeListe & a2) const;
00110   void debug(int decal = 0)const{
00111     for (int i=0; i< decal; i++) std::cout << " ";
00112     std::cout << "AtomeListe : ( & = " << this << " symb=\"" << symb << "\" Zed = " << Zed 
00113         << " nb = " << nb << " no = " << no 
00114         << " suiv = " << suiv << " group = " << group
00115         << ")\n";
00116     if(group) group->debug(2+decal);
00117     if(suiv) suiv->debug(decal);
00118   };
00119 };
00120 
00121 typedef enum { aqueous, gas, sol } moltype;
00122 
00123 extern const char* moltypeStr[]; /* les chaînes aq, g,s */
00124 
00125 class Membre;
00126 
00127 class Molec{
00128   AtomeListe * al;
00129   int ch;
00130   fraction nb;
00131   int no;
00132   moltype t;
00133  public:
00134   Molec(AtomeListe * a, int c = 0, int n=1, int d=1): 
00135     al(a), ch(c), nb(n,d), t(aqueous){};
00136   Molec(const Molec & m):
00137     al(m.al), ch(m.ch), nb(m.nb.i,m.nb.d), t(m.t) {}
00138   AtomeListe & liste()const{return *al;};
00139   int charge()const{return ch;};
00140   bool eqMol(const Molec * m) const {
00141     return (al->isEqual(*(m->al))) && (ch== m->ch);
00142   }
00143   void nombre(int n, int d=1){nb=fraction(n,d);};
00144   fraction nombre()const{return nb;};
00145   void add(fraction f);
00146   void sub(fraction f);
00147   moltype typage()const{return t;};
00148   void typage(moltype at){t=at;};
00149   void numero(int n){no=n;};
00150   int numero()const{return no;};
00151   void triage(){al = AtomeListe::triage(al);};
00152   void compte(Compteur & c)const{if (al) al->compte(c,nb);};
00153   double weight(void)const{if (al) return al->weight(nb); else return 0.0;};
00154   const std::string signature()const;
00155   void printNombre(std::ostream & o)const;
00156   bool printcount(std::ostream & o, bool first) const;
00157   bool printelec(std::ostream & o, bool first) const;
00158   bool printspecies(std::ostream & o, bool first) const;
00159   void printnorm(std::ostream & o)const;
00160   void printweigh(std::ostream & o)const;
00161   void coeff( fraction f);
00162   bool printNernst(std::ostream & o, const char * prefix ="");
00163   bool printNernstWIMS(std::ostream & o, bool wantedlatex);
00164   bool iswater()const;
00165   bool iselectron()const;
00166   fraction  nbelectron()const;
00167   void debug(int decal = 0)const{
00168     for (int i=0; i < decal; i++) std::cout << " ";
00169     std::cout << "Molec : ( " << this << " charge = " << ch 
00170         << " nombre = " << nb << " no = " << no;
00171     al->debug(decal+2);
00172     std::cout << ")\n";
00173   };
00174   // two Molecs are equal if the AtomLists and the charges are equal.
00175   friend Membre operator & (Membre & m1, Membre & m2);
00176   friend Membre operator - (Membre & m1, Membre & m2);
00177 };
00178 
00179 std::ostream & operator << (std::ostream & o, const AtomeListe & l);
00180 std::ostream & operator << (std::ostream & o, const Molec & m);
00181 
00182 class Membre : public std::vector<Molec *>{
00183 public:
00184   int findMol(const Molec *);
00185   void addMol(const Molec *);
00186   void addMembre(const Membre *);
00187   void eraseNull();
00188   void compte(Compteur & c)const;
00189   void numerote();
00190   void triage();
00191   void printnorm(std::ostream & o) const;
00192   void printcount(std::ostream & o) const;
00193   void printelec(std::ostream & o) const;
00194   void printspecies(std::ostream & o) const;
00195   void printweight(std::ostream & o) const;
00196   void coeff( fraction f);
00197   void printNernst(std::ostream & o);
00198   void printNernstWIMS(std::ostream & o, bool wantedlatex);
00199   int printableNernst();
00200   bool redox()const;
00201   fraction  nbelectron()const;
00202   void debug(int decal = 0)const{
00203     for (int i=0; i < decal; i++) std::cout << " ";
00204     std::cout << "Membre : ( " << this;
00205     for (int j=0; j < size(); j++){
00206       std::cout << j << " :\n";
00207       operator[](j)->debug(decal+2);
00208     }
00209     std::cout << "\n";
00210   }
00211 };
00212 
00213 // intersection between two Membres
00214 Membre operator & (Membre & m1, Membre & m2);
00215 // members of first set which are not in the second
00216 Membre operator - (Membre & m1, Membre & m2);
00217 
00218 std::ostream & operator << (std::ostream & o, const Membre & m);
00219 
00220 class Chemeq{
00221   Membre * gauche, * droit;
00222   std::string cste;
00223   long double val;
00224 public:
00225   Chemeq(Membre * g, Membre * d) : gauche (g), droit(d), val(MINVAL){};
00226   const Membre * membredroit()const{return droit;};
00227   const Membre * membregauche()const{return gauche;};
00228   void addChemeq(const Chemeq *);
00229   void subChemeq(const Chemeq *);
00230   void simplifie(bool tri);
00231   void numerote(){gauche->numerote(); droit->numerote();};
00232   void triage(){gauche->triage(); droit->triage();};
00233   /* ajuste le coefficient pour qu'il y ait 1 mol du premier réactif */
00234   void coeff1();
00235   /* mutiplie par la fraction num/den */
00236   void multiply(int num, int den);
00237   fraction nbelectron()const{return gauche->nbelectron()-droit->nbelectron();};
00238   /* renvoie val ou nbelectron()*Faraday*val */
00239   long double enthalpy() const;
00240   void normalise(){numerote(); triage(); coeff1();};
00241   void printnorm(std::ostream & o);
00242   void printcount(std::ostream & o) const;
00243   void printelec(std::ostream & o) const;
00244   void printspecies(std::ostream & o) const;
00245   void printweight(std::ostream & o) const;
00246   void printNernst(std::ostream & o, std::ostream & w, bool wantedlatex=false);
00247   std::string equilibre();
00248   bool redox()const;
00249   const std::string constante()const{ return cste;};
00250   void constante (const std::string s) { cste = s;};
00251   bool valdefined()const;
00252   double valeur()const{return val;};
00253   std::string valeur_latex()const;
00254   void valeur(double r){val=r;};
00255 };
00256 
00257 std::ostream & operator << (std::ostream & o, const Chemeq & c);
00258 //struct taken from Kyle Burton's gperiodic
00259 
00260 /* structure to hold element data, as initialized from the static
00261  * mendeleiev.c */
00262 enum info_types {
00263   NAME, SYMBOL, NUMBER, WEIGHT, MELTING, BOILING, PAULING,
00264   MAX_INFO_NR      /* Has to be the last element */
00265 };
00266 
00267 struct table_entry {
00268   const char *info[MAX_INFO_NR];
00269 };
00270 
00271 extern struct table_entry table[];
00272 
00273 double mendelweight(int i);
00274 int findmendel(const char * symb);
00275 double mendelweight(const char * symb);
00276 
00277 #endif