// // cmv 05/08/96 // #include "defs.h" #include #include #include #include #ifndef __mac__ #include #endif #include "histos2.h" #include "generalfit.h" //++ // Class Histo2D // Lib Outils++ // include histos2.h // // Classe d'histogrammes 2D //-- /////////////////////////////////////////////////////////////////// //++ // Titre Constructeurs //-- //++ Histo2D::Histo2D(float xMin, float xMax, int nxBin ,float yMin, float yMax, int nyBin) // // Createur d'un histogramme 2D ayant nxBin,nyBin bins // entre xMin,xMax et yMin,yMax. //-- : data(new float[nxBin*nyBin]), err2(NULL) , nHist(0), nEntries(0) , nx(nxBin), ny(nyBin), nxy(nxBin*nyBin) , xmin(xMin), xmax(xMax), ymin(yMin), ymax(yMax) , wbinx((xMax - xMin)/nxBin), wbiny((yMax - yMin)/nyBin) , hprojx(NULL), hprojy(NULL) { DBASSERT(nxBin>0 && nyBin>0 && xMin0) { SetSliX(nb); for(i=0; i0) { SetSliY(nb); for(i=0; i0) { for(i=0; i0) { for(i=0; i 0 ) { if(err2==NULL) err2 = new double[nxy]; memset(err2, 0, nxy*sizeof(double)); } } /////////////////////////////////////////////////////////////////// //++ Histo2D& Histo2D::operator = (const Histo2D& h) // //-- { int i,j,nb; float min,max; if(this == &h) return *this; if( h.nxy > nxy ) Delete(); if(!data) data = new float[h.nxy]; if( !h.err2 && err2 ) { delete [] err2; err2=NULL;} if( h.err2 && !err2 ) err2 = new double[h.nxy]; for(i=0;i<3;i++) for(j=0;j<3;j++) over[i][j] = h.over[i][j]; nHist = h.nHist; nEntries = h.nEntries; nx = h.nx; ny = h.ny; nxy = h.nxy; xmin = h.xmin; xmax = h.xmax; wbinx = h.wbinx; ymin = h.ymin; ymax = h.ymax; wbiny = h.wbiny; memcpy(data, h.data, nxy*sizeof(float)); if(err2) memcpy(err2, h.err2, nxy*sizeof(double)); DelProjX(); if(h.hprojx) { SetProjX(); *hprojx = *(h.hprojx); } DelProjY(); if(h.hprojy) { SetProjY(); *hprojy = *(h.hprojy); } DelSliX(); nb = h.NSliX(); if(nb>0) { SetSliX(nb); for(i=0; i0) { SetSliY(nb); for(i=0; i0) { for(i=0; i0) { for(i=0; i0) for(i=0; i0) for(i=0; i0) for(i=0; i0) for(i=0; i0) for(i=0; i0) for(i=0; i0) for(i=0; i0) for(i=0; i0) for(i=0; i0) for(i=0; i0) for(i=0; i0) for(i=0; i0) for(i=0; i0) for(i=0; i0) for(i=0; i0) for(i=0; i i = coord x (0 ii = ligne (0ii et j<->jj //| ce qui, en representation classique des histos2D et des matrices //| entraine une inversion x<->y cad une symetrie / diagonale principale //| H(0,...) represente ^ mais v(0,...) represente //| |x....... |xxxxxxxx| //| |x....... |........| //| |x....... |........| //| |x....... |........| //| |x....... |........| //| ---------> //| colonne no 1 ligne no 1 //-- //++ void Histo2D::GetValue(Matrix &v) // // Remplissage d'un tableau avec les valeurs du contenu. //-- { v.Realloc(nx,ny); for(int i=0;i0.) Error2(i,j) += v(i,j); return; } //++ void Histo2D::PutError(Matrix &v) // // Remplissage des erreurs de l'histo avec les valeurs d'un tableau. //-- { int i,j; if(v.NRows()!=nx || v.NCol()!=ny) THROW(sizeMismatchErr); if(!err2) Errors(); for(i=0;i0.) Error2(i,j)=v(i,j)*v(i,j); else Error2(i,j)= -v(i,j)*v(i,j); return; } /////////////////////////////////////////////////////////////////// /********* Methode *********/ //++ void Histo2D::Add(float x, float y, float w) // // Addition du contenu de l'histo pour x,y poids w. //-- { list::iterator it; int i,j; FindBin(x,y,i,j); if( hprojx != NULL ) hprojx->Add(x,w); if( hprojy != NULL ) hprojy->Add(y,w); if(lbandx.size()>0) for( it = lbandx.begin(); it != lbandx.end(); it++) if( (*it).min <= y && y < (*it).max ) (*it).H->Add(x,w); if(lbandy.size()>0) for( it = lbandy.begin(); it != lbandy.end(); it++) if( (*it).min <= x && x < (*it).max ) (*it).H->Add(y,w); if(lslix.size()>0) for( it = lslix.begin(); it != lslix.end(); it++) if( (*it).min <= y && y < (*it).max ) (*it).H->Add(x,w); if(lsliy.size()>0) for( it = lsliy.begin(); it != lsliy.end(); it++) if( (*it).min <= x && x < (*it).max ) (*it).H->Add(y,w); if( i<0 || i>=nx || j<0 || j>=ny ) { if(i<0) i=0; else if(i>=nx) i=2; else i=1; if(j<0) j=0; else if(j>=ny) j=2; else j=1; over[i][j] += w; over[1][1] += w; return; } data[j*nx+i] += w; if(err2!=NULL) err2[j*nx+i] += w*w; nHist += w; nEntries++; } /////////////////////////////////////////////////////////////////// //++ void Histo2D::IJMax(int& imax,int& jmax,int il,int ih,int jl,int jh) // // Recherche du bin du maximum dans le pave [il,ih][jl,jh]. //-- { if( il > ih ) { il = 0; ih = nx-1; } if( jl > jh ) { jl = 0; jh = ny-1; } if( il < 0 ) il = 0; if( jl < 0 ) jl = 0; if( ih >= nx ) ih = nx-1; if( jh >= ny ) jh = ny-1; imax = jmax = 0; if(nxy==1) return; float mx=(*this)(il,jl); for (int i=il; i<=ih; i++) for (int j=jl; j<=jh; j++) if ((*this)(i,j)>mx) {imax = i; jmax = j; mx=(*this)(i,j);} } //++ void Histo2D::IJMin(int& imax,int& jmax,int il,int ih,int jl,int jh) // // Recherche du bin du minimum dans le pave [il,ih][jl,jh]. //-- { if( il > ih ) { il = 0; ih = nx-1; } if( jl > jh ) { jl = 0; jh = ny-1; } if( il < 0 ) il = 0; if( jl < 0 ) jl = 0; if( ih >= nx ) ih = nx-1; if( jh >= ny ) jh = ny-1; imax = jmax = 0; if(nxy==1) return; float mx=(*this)(il,jl); for (int i=il; i<=ih; i++) for (int j=jl; j<=jh; j++) if ((*this)(i,j) ih ) { il = 0; ih = nx-1; } if( jl > jh ) { jl = 0; jh = ny-1; } if( il < 0 ) il = 0; if( jl < 0 ) jl = 0; if( ih >= nx ) ih = nx-1; if( jh >= ny ) jh = ny-1; float mx=(*this)(il,jl); if(nxy==1) return mx; for (int i=il; i<=ih; i++) for (int j=jl; j<=jh; j++) if ((*this)(i,j)>mx) mx=(*this)(i,j); return mx; } //++ float Histo2D::VMin(int il,int ih,int jl,int jh) const // // Recherche du minimum dans le pave [il,ih][jl,jh]. //-- { if( il > ih ) { il = 0; ih = nx-1; } if( jl > jh ) { jl = 0; jh = ny-1; } if( il < 0 ) il = 0; if( jl < 0 ) jl = 0; if( ih >= nx ) ih = nx-1; if( jh >= ny ) jh = ny-1; float mx=(*this)(il,jl); if(nxy==1) return mx; for (int i=il; i<=ih; i++) for (int j=jl; j<=jh; j++) if ((*this)(i,j)=3 || j < 0 || j>=3 ) return over[1][1]; return over[i][j]; } /////////////////////////////////////////////////////////////////// //++ int Histo2D::BinNonNul() const // // Retourne le nombre de bins non-nuls. //-- { int non=0; for (int i=0;i= nx ) return -1; if( jm < 0 || jm >= ny ) return -1; if( SzPav%2 == 0 ) SzPav++; SzPav = (SzPav-1)/2; int rc = 0; double dxm = 0, dym = 0, wx = 0; for(int i=im-SzPav;i<=im+SzPav;i++) { if( i<0 || i>= nx ) {rc=1; continue;} for(int j=jm-SzPav;j<=jm+SzPav;j++) { if( j<0 || j>= ny ) {rc=1; continue;} float x,y; BinCenter(i,j,x,y); dxm += x * (*this)(i,j); dym += y * (*this)(i,j); wx += (*this)(i,j); } } if( wx > 0. ) { xm = dxm/wx; ym = dym/wx; return rc; } else { BinCenter(im,jm,xm,ym); return 2; } } //++ int Histo2D::FindMax(int& im,int& jm,int SzPav,float Dz ,int il,int ih,int jl,int jh) // // Pour trouver le maximum de l'histogramme en tenant compte // des fluctuations. //| Methode: //| 1-/ On recherche le bin maximum MAX de l'histogramme //| 2-/ On considere que tous les pixels compris entre [MAX-Dz,MAX] //| peuvent etre des pixels maxima. //| 3-/ On identifie le bin maximum en choissisant le pixel du 2-/ //| tel que la somme des pixels dans un pave SzPav x SzPav soit maximale. //| INPUT: //| SzPav = taille du pave pour departager //| Dz = tolerance pour identifier tous les pixels "maximum" //| OUTPUT: //| im,jm = pixel maximum trouve //| RETURN: //| <0 = Echec //| >0 = nombre de pixels possibles pour le maximum //-- { if( il > ih ) { il = 0; ih = nx-1; } if( jl > jh ) { jl = 0; jh = ny-1; } if( il < 0 ) il = 0; if( jl < 0 ) jl = 0; if( ih >= nx ) ih = nx-1; if( jh >= ny ) jh = ny-1; if( SzPav < 0 ) SzPav = 0; else { if( SzPav%2 == 0 ) SzPav++; SzPav = (SzPav-1)/2;} if( Dz < 0 ) Dz = 0.; float max = VMax(il,ih,jl,jh) - Dz; int nmax = 0; float sumx = -MAXFLOAT; for(int i=il;i<=ih;i++) for(int j=jl;j<=jh;j++) { if( (*this)(i,j) < max) continue; nmax++; float sum = 0.; for(int ii=i-SzPav;ii<=i+SzPav;ii++) { if( ii<0 || ii >= nx ) continue; for(int jj=j-SzPav;jj<=j+SzPav;jj++) { if( jj<0 || jj >= ny ) continue; sum += (*this)(ii,jj); } } if( sum > sumx ) { im = i; jm = j; sumx = sum;} } if( nmax <= 0 ) { IJMax(im,jm,il,ih,jl,jh); return 1;} return nmax; } ////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////// //++ int Histo2D::Fit(GeneralFit& gfit,unsigned short typ_err) // // Fit de l'histogramme par ``gfit''. //| typ_err = 0 : //| - erreur attachee au bin si elle existe //| - sinon 1 //| typ_err = 1 : //| - erreur attachee au bin si elle existe //| - sinon max( sqrt(abs(bin) ,1 ) //| typ_err = 2 : //| - erreur forcee a 1 //| typ_err = 3 : //| - erreur forcee a max( sqrt(abs(bin) ,1 ) //| typ_err = 4 : //| - erreur forcee a 1, nulle si bin a zero. //| typ_err = 5 : //| - erreur forcee a max( sqrt(abs(bin) ,1 ), //| nulle si bin a zero. //-- { if(NBinX()*NBinY()<=0) return -1000; if(typ_err>5) typ_err=0; GeneralFitData mydata(2,NBinX()*NBinY()); for(int i=0;iValue(x,par.Data()); } return h2; } //++ Histo2D* Histo2D::FitFunction(GeneralFit& gfit) // // Retourne une classe contenant la fonction du fit ``gfit''. //-- { if(NBinX()<=0 || NBinY()<=0) return NULL; GeneralFunction* f = gfit.GetFunction(); if(f==NULL) return NULL; Vector par = gfit.GetParm(); Histo2D* h2 = new Histo2D(*this); for(int i=0;iValue(x,par.Data()); } return h2; } /////////////////////////////////////////////////////////////////// //++ void Histo2D::PrintStatus() // // Impression des informations sur l'histogramme. //-- { printf("~Histo::Print nHist=%g nEntries=%d\n",nHist,nEntries); printf("over: [ %g %g %g // %g %g %g // %g %g %g ]\n" ,over[2][0],over[2][1],over[2][2] ,over[1][0],over[1][1],over[1][2] ,over[0][0],over[0][1],over[0][2]); printf(" nx=%d xmin=%g xmax=%g binx=%g ",nx,xmin,xmax,wbinx); printf(" ny=%d ymin=%g ymax=%g biny=%g\n",ny,ymin,ymax,wbiny); } /////////////////////////////////////////////////////////////////// //++ void Histo2D::Print(float min,float max ,int il,int ih,int jl,int jh) // // Impression de l'histogramme sur stdout entre [il,ih] et [jl,jh]. //-- { int ns = 35; // numero d'index: 00000000001111111111222222222233333 // 01234567890123456789012345678901234 // valeur entiere: 00000000001111111111222222222233333 // 12345678901234567890123456789012345 const char *s = "+23456789ABCDEFGHIJKLMNOPQRSTUVWXYZ"; if( il > ih ) { il = 0; ih = nx-1; } if( jl > jh ) { jl = 0; jh = ny-1; } if( il < 0 ) il = 0; if( jl < 0 ) jl = 0; if( ih >= nx ) ih = nx-1; if( jh >= ny ) jh = ny-1; PrintStatus(); if( il != 0 || ih != nx-1 || jl != 0 || jh != ny-1 ) { float xl,xh,yl,yh; BinLowEdge(il,jl,xl,yl); BinHighEdge(ih,jh,xh,yh); printf(" impression"); printf(" en X: %d=[%d,%d] xmin=%g xmax=%g " ,ih-il+1,il,ih,xl,xh); printf(" en Y: %d=[%d,%d] ymin=%g ymax=%g\n" ,jh-jl+1,jl,jh,yl,yh); } if(min >= max) { if(min != 0.) min = VMin(il,ih,jl,jh); else min=0.; max = VMax(il,ih,jl,jh); } if(min>max) return; if(min==max) {min -= 1.; max += 1.;} printf(" min=%g max=%g\n",min,max); // imprime numero de bin en colonne printf("\n"); if( nx-1 >= 100 ) { printf(" "); for(int i=il;i<=ih;i++) printf("%1d",(int) (i%1000)/100); printf("\n"); } if( nx-1 >= 10 ) { printf(" "); for(int i=il;i<=ih;i++) printf("%1d",(int) (i%100)/10); printf("\n"); } printf(" "); for(int i=il;i<=ih;i++) printf("%1d",i%10); printf("\n"); printf(" "); {for(int i=il;i<=ih;i++) printf("-"); printf("\n");} // imprime histogramme for(int j=jh;j>=jl;j--) { printf("%3d: ",j); for(int i=il;i<=ih;i++) { int h; if( 1<=max-min && max-min<=35 ) h = (int)( (*this)(i,j) - min ) - 1; else h = (int)( ((*this)(i,j)-min)/(max-min) * ns ) - 1; char c; if(h<0 && (*this)(i,j)>min) c = '.'; else if(h<0) c = ' '; else if(h>=ns) c = '*'; else c = s[h]; printf("%c",c); } printf("\n"); } // imprime numero de bin en colonne printf(" "); {for(int i=il;i<=ih;i++) printf("-"); printf("\n");} if( nx-1 >= 100 ) { printf(" "); for(int i=il;i<=ih;i++) printf("%1d",(int) (i%1000)/100); printf("\n"); } if( nx-1 >= 10 ) { printf(" "); for(int i=il;i<=ih;i++) printf("%1d",(int) (i%100)/10); printf("\n"); } printf(" "); {for(int i=il;i<=ih;i++) printf("%1d",i%10);} printf("\n"); } // Rappel des inline functions pour commentaires //++ // inline float XMin() // Retourne l'abscisse minimum. //-- //++ // inline float XMax() // Retourne l'abscisse maximum. //-- //++ // inline float YMin() // Retourne l'ordonnee minimum. //-- //++ // inline float YMax() // Retourne l'ordonnee maximum. //-- //++ // inline int NBinX() // Retourne le nombre de bins selon X. //-- //++ // inline int NBinY() // Retourne le nombre de bins selon Y. //-- //++ // inline float WBinX() // Retourne la largeur du bin selon X. //-- //++ // inline float WBinY() // Retourne la largeur du bin selon Y. //-- //++ // inline float* Bins() const // Retourne le pointeur sur le tableaux des contenus. //-- //++ // inline float operator()(int i,int j) const // Retourne le contenu du bin i,j. //-- //++ // inline float& operator()(int i,int j) // Remplit le contenu du bin i,j. //-- //++ // inline float Error(int i,int j) const // Retourne l'erreur du bin i,j. //-- //++ // inline double Error2(int i,int j) const // Retourne l'erreur au carre du bin i,j. //-- //++ // inline double& Error2(int i,int j) // Remplit l'erreur au carre du bin i,j. //-- //++ // inline float NData() const // Retourne la somme ponderee. //-- //++ // inline int NEntries() const // Retourne le nombre d'entrees. //-- //++ // inline void BinLowEdge(int i,int j,float& x,float& y) // Retourne l'abscisse et l'ordonnee du coin inferieur du bin i,j. //-- //++ // inline void BinCenter(int i,int j,float& x,float& y) // Retourne l'abscisse et l'ordonnee du centre du bin i,j. //-- //++ // inline void BinHighEdge(int i,int j,float& x,float& y) // Retourne l'abscisse et l'ordonnee du coin superieur du bin i,j. //-- //++ // inline void FindBin(float x,float y,int& i,int& j) // Retourne les numeros du bin contenant l'abscisse et l'ordonnee x,y. //-- /////////////////////////////////////////////////////////////////// //++ // Titre Methodes pour gerer les projections //-- //++ void Histo2D::SetProjX() // // Pour creer la projection X. //-- { if( hprojx != NULL ) DelProjX(); hprojx = new Histo(xmin,xmax,nx); if( err2 != NULL && hprojx != NULL ) hprojx->Errors(); } //++ void Histo2D::SetProjY() // // Pour creer la projection Y. //-- { if( hprojy != NULL ) DelProjY(); hprojy = new Histo(ymin,ymax,ny); if( err2 != NULL && hprojy != NULL ) hprojy->Errors(); } //++ void Histo2D::SetProj() // // Pour creer les projections X et Y. //-- { SetProjX(); SetProjY(); } //++ void Histo2D::ShowProj() // // Informations sur les projections. //-- { if( hprojx != NULL ) cout << ">>>> Projection X set : "<< hprojx <>>> NO Projection X set"<>>> Projection Y set : "<< hprojy <>>> NO Projection Y set"<Zero(); } //++ void Histo2D::ZeroProjY() // // Remise a zero de la projection selon Y. //-- { if( hprojy == NULL ) return; hprojy->Zero(); } //++ void Histo2D::ZeroProj() // // Remise a zero des projections selon X et Y. //-- { ZeroProjX(); ZeroProjY(); } // Rappel des inline functions pour commentaires //++ // inline Histo* HProjX() // Retourne le pointeur sur l'histo 1D de la projection selon X. //-- //++ // inline Histo* HProjY() // Retourne le pointeur sur l'histo 1D de la projection selon Y. //-- /////////////////////////////////////////////////////////////////// //++ // Titre Methodes pour gerer les bandes //-- //++ int Histo2D::SetBandX(float ybmin,float ybmax) // // Pour creer une bande en X entre ybmin et ybmax. //-- { b_s.num = lbandx.size(); b_s.min = ybmin; b_s.max = ybmax; b_s.H = new Histo(xmin,xmax,nx); lbandx.push_back(b_s); b_s.H = NULL; return lbandx.size()-1; } //++ int Histo2D::SetBandY(float xbmin,float xbmax) // // Pour creer une bande en Y entre xbmin et xbmax. //-- { b_s.num = lbandy.size(); b_s.min = xbmin; b_s.max = xbmax; b_s.H = new Histo(ymin,ymax,ny); lbandy.push_back(b_s); b_s.H = NULL; return lbandy.size()-1; } //++ void Histo2D::DelBandX() // // Destruction des histogrammes des bandes selon X. //-- { if( lbandx.size() <= 0 ) return; for(list::iterator i = lbandx.begin(); i != lbandx.end(); i++) if( (*i).H != NULL ) {delete (*i).H; (*i).H=NULL;} lbandx.erase(lbandx.begin(),lbandx.end()); } //++ void Histo2D::DelBandY() // // Destruction des histogrammes des bandes selon Y. //-- { if( lbandy.size() <= 0 ) return; for(list::iterator i = lbandy.begin(); i != lbandy.end(); i++) if( (*i).H != NULL ) {delete (*i).H; (*i).H=NULL;} lbandy.erase(lbandy.begin(),lbandy.end()); } //++ void Histo2D::ZeroBandX() // // Remise a zero des bandes selon X. //-- { if( lbandx.size() <= 0 ) return; list::iterator i; for(i = lbandx.begin(); i != lbandx.end(); i++) (*i).H->Zero(); } //++ void Histo2D::ZeroBandY() // // Remise a zero des bandes selon Y. //-- { if( lbandy.size() <= 0 ) return; list::iterator i; for(i = lbandy.begin(); i != lbandy.end(); i++) (*i).H->Zero(); } //++ Histo* Histo2D::HBandX(int n) const // // Retourne un pointeur sur la bande numero `n' selon X. //-- { if( lbandx.size() <= 0 || n < 0 || n >= (int) lbandx.size() ) return NULL; for(list::const_iterator i = lbandx.begin(); i != lbandx.end(); i++) if( (*i).num == n ) return (*i).H; return NULL; } //++ Histo* Histo2D::HBandY(int n) const // // Retourne un pointeur sur la bande numero `n' selon Y. //-- { if( lbandy.size() <= 0 || n < 0 || n >= (int) lbandy.size() ) return NULL; for(list::const_iterator i = lbandy.begin(); i != lbandy.end(); i++) if( (*i).num == n ) return (*i).H; return NULL; } //++ void Histo2D::GetBandX(int n,float& ybmin,float& ybmax) const // // Retourne les limites de la bande numero `n' selon X. //-- { ybmin = 0.; ybmax = 0.; if( lbandx.size() <= 0 || n < 0 || n >= (int) lbandx.size() ) return; for(list::const_iterator i = lbandx.begin(); i != lbandx.end(); i++) if( (*i).num == n ) { ybmin = (*i).min; ybmax = (*i).max; return;} return; } //++ void Histo2D::GetBandY(int n,float& xbmin,float& xbmax) const // // Retourne les limites de la bande numero `n' selon Y. //-- { xbmin = 0.; xbmax = 0.; if( lbandy.size() <= 0 || n < 0 || n >= (int) lbandy.size() ) return; for(list::const_iterator i = lbandy.begin(); i != lbandy.end(); i++) if( (*i).num == n ) { xbmin = (*i).min; xbmax = (*i).max; return;} return; } //++ void Histo2D::ShowBand(int lp) // // Informations sur les bandes. //-- { cout << ">>>> Nombre de bande X : " << lbandx.size() << endl; if( lp>0 && lbandx.size()>0 ) { list::iterator i; for(i = lbandx.begin(); i != lbandx.end(); i++) { cout<<" "<<(*i).num<<" de ymin="<<(*i).min<<" a ymax="<<(*i).max; if(lp>1) cout << " H=" << (*i).H; cout << endl; } } cout << ">>>> Nombre de bande Y : " << lbandy.size() << endl; if( lp>0 && lbandy.size()>0 ) { list::iterator i; for(i = lbandy.begin(); i != lbandy.end(); i++) { cout<<" "<<(*i).num<<" de xmin="<<(*i).min<<" a xmax="<<(*i).max; if(lp>1) cout << " H=" << (*i).H; cout << endl; } } } // Rappel des inline functions pour commentaires //++ // inline int NBandX() // Retourne le nombre de bandes selon X //-- //++ // inline int NBandY() // Retourne le nombre de bandes selon Y //-- /////////////////////////////////////////////////////////////////// //++ // Titre Methodes pour gerer les bandes equidistantes //-- //++ int Histo2D::SetSliX(int nsli) // // Pour creer `nsli' bandes equidistantes selon X. //-- { if( nsli <= 0 ) return -1; if( nsli > ny ) nsli = ny; if( lslix.size() > 0 ) DelSliX(); float w = (ymax-ymin)/nsli; for(int i=0; i nx ) nsli = nx; if( lsliy.size() > 0 ) DelSliY(); float w = (xmax-xmin)/nsli; for(int i=0; i::iterator i = lslix.begin(); i != lslix.end(); i++) if( (*i).H != NULL ) {delete (*i).H; (*i).H=NULL;} lslix.erase(lslix.begin(),lslix.end()); } //++ void Histo2D::DelSliY() // // Destruction des bandes equidistantes selon Y. //-- { if( lsliy.size() <= 0 ) return; for(list::iterator i = lsliy.begin(); i != lsliy.end(); i++) if( (*i).H != NULL ) {delete (*i).H; (*i).H=NULL;} lsliy.erase(lsliy.begin(),lsliy.end()); } //++ void Histo2D::ZeroSliX() // // Remise a zero des bandes equidistantes selon X. //-- { if( lslix.size() <= 0 ) return; list::iterator i; for(i = lslix.begin(); i != lslix.end(); i++) (*i).H->Zero(); } //++ void Histo2D::ZeroSliY() // // Remise a zero des bandes equidistantes selon Y. //-- { if( lsliy.size() <= 0 ) return; list::iterator i; for(i = lsliy.begin(); i != lsliy.end(); i++) (*i).H->Zero(); } //++ Histo* Histo2D::HSliX(int n) const // // Retourne un pointeur sur la bande equidistante numero `n' // selon X. //-- { if( lslix.size() <= 0 || n < 0 || n >= (int) lslix.size() ) return NULL; for(list::const_iterator i = lslix.begin(); i != lslix.end(); i++) if( (*i).num == n ) return (*i).H; return NULL; } //++ Histo* Histo2D::HSliY(int n) const // // Retourne un pointeur sur la bande equidistante numero `n' // selon Y. //-- { if( lsliy.size() <= 0 || n < 0 || n >= (int) lsliy.size() ) return NULL; for(list::const_iterator i = lsliy.begin(); i != lsliy.end(); i++) if( (*i).num == n ) return (*i).H; return NULL; } //++ void Histo2D::ShowSli(int lp) // // Informations sur les bandes equidistantes. //-- { list::iterator i; cout << ">>>> Nombre de slice X : " << lslix.size() << endl; if( lp>0 && lslix.size() > 0 ) for(i = lslix.begin(); i != lslix.end(); i++) { cout<<" "<<(*i).num<<" de ymin="<<(*i).min<<" a ymax="<<(*i).max; if(lp>1) cout << " H=" << (*i).H; cout << endl; } cout << ">>>> Nombre de slice Y : " << lsliy.size() << endl; if( lp>0 && lsliy.size()>0 ) for(i = lsliy.begin(); i != lsliy.end(); i++) { cout<<" "<<(*i).num<<" de xmin="<<(*i).min<<" a xmax="<<(*i).max; if(lp>1) cout << " H=" << (*i).H; cout << endl; } } // Rappel des inline functions pour commentaires //++ // inline int NSliX() // Retourne le nombre de slices selon X //-- //++ // inline int NSliY() // Retourne le nombre de slices selon Y //-- /////////////////////////////////////////////////////////////////// //++ // Titre Methodes pour ecriture ppersist //-- //++ void Histo2D::WriteSelf(POutPersist& s) const // // Ecriture fichier de type ppersist. //-- { char strg[256]; int j; float min,max; Histo* h; // Que faut-il ecrire? int_4 errok = (err2) ? 1 : 0; int_4 projx = (hprojx) ? 1 : 0; int_4 projy = (hprojy) ? 1 : 0; int_4 nslix = NSliX(); int_4 nsliy = NSliY(); int_4 nbanx = NBandX(); int_4 nbany = NBandY(); // Ecriture entete pour identifier facilement sprintf(strg,"nx=%d ny=%d nxy=%d errok=%1d",nx,ny,nxy,errok); s.PutLine(strg); sprintf(strg,"nHist=%g nEntries=%d",nHist,nEntries); s.PutLine(strg); sprintf(strg,"wbinx=%g wbiny=%g",wbinx,wbiny); s.PutLine(strg); sprintf(strg,"xmin=%g xmax=%g ymin=%g ymax=%g",xmin,xmax,ymin,ymax); s.PutLine(strg); sprintf(strg,"projx/y=%d %d nbandx/y=%d %d nbslix/y=%d %d" ,projx,projy,nbanx,nbany,nslix,nsliy); s.PutLine(strg); sprintf(strg,"over %g %g %g %g %g %g %g %g %g" ,over[0][0],over[0][1],over[0][2] ,over[1][0],over[1][1],over[1][2] ,over[2][0],over[2][1],over[2][2]); s.PutLine(strg); // Ecriture variables de definitions s.PutI4(nx); s.PutI4(ny); s.PutI4(nxy); s.PutI4(errok); s.PutI4(nEntries); s.PutR8(nHist); s.PutR4(xmin); s.PutR4(xmax); s.PutR4(ymin); s.PutR4(ymax); s.PutR4(wbinx); s.PutR4(wbiny); s.PutR4s(&over[0][0],9); s.PutI4(projx); s.PutI4(projy); s.PutI4(nslix); s.PutI4(nsliy); s.PutI4(nbanx); s.PutI4(nbany); // Ecriture histo2D sprintf(strg,"Histo2D: Tableau des donnees %d = %d * %d",nxy,nx,ny); s.PutLine(strg); for(j=0;jWrite(s); } if(projy) { sprintf(strg,"Histo2D: Projection Y"); s.PutLine(strg); hprojy->Write(s); } // Ecriture des slices if(nslix>0) { sprintf(strg,"Histo2D: Slices X %d",nslix); s.PutLine(strg); for(j=0;jWrite(s); } } if(nsliy>0) { sprintf(strg,"Histo2D: Slices Y %d",nsliy); s.PutLine(strg); for(j=0;jWrite(s); } } // Ecriture des bandes if( nbanx>0 ) { sprintf(strg,"Histo2D: Bandes X %d",nbanx); s.PutLine(strg); list::const_iterator it; for(it = lbandx.begin(); it != lbandx.end(); it++) { min = (*it).min; max = (*it).max; s.PutR4(min); s.PutR4(max); } for(it = lbandx.begin(); it != lbandx.end(); it++) { h = (*it).H; h->Write(s); } } if( nbany>0 ) { sprintf(strg,"Histo2D: Bandes Y %d",nbany); s.PutLine(strg); list::const_iterator it; for(it = lbandy.begin(); it != lbandy.end(); it++) { min = (*it).min; max = (*it).max; s.PutR4(min); s.PutR4(max); } for(it = lbandy.begin(); it != lbandy.end(); it++) { h = (*it).H; h->Write(s); } } return; } //++ void Histo2D::ReadSelf(PInPersist& s) // // Lecture fichier de type ppersist. //-- { Delete(); int j; float min,max; Histo* h; char strg[256]; int_4 errok, projx, projy, nslix, nsliy, nbanx, nbany; // Lecture entete s.GetLine(strg, 255); s.GetLine(strg, 255); s.GetLine(strg, 255); s.GetLine(strg, 255); s.GetLine(strg, 255); s.GetLine(strg, 255); // Lecture variables de definitions s.GetI4(nx); s.GetI4(ny); s.GetI4(nxy); s.GetI4(errok); s.GetI4(nEntries); s.GetR8(nHist); s.GetR4(xmin); s.GetR4(xmax); s.GetR4(ymin); s.GetR4(ymax); s.GetR4(wbinx); s.GetR4(wbiny); s.GetR4s(&over[0][0],9); s.GetI4(projx); s.GetI4(projy); s.GetI4(nslix); s.GetI4(nsliy); s.GetI4(nbanx); s.GetI4(nbany); // Lecture histo2D data = new float[nxy]; s.GetLine(strg, 255); for(j=0;jRead(s); } if(projy) { s.GetLine(strg, 255); SetProjY(); hprojy->Read(s); } // Lecture des slices if(nslix>0) { s.GetLine(strg, 255); SetSliX(nslix); DBASSERT (nslix==NSliX()); for(j=0;jRead(s); } if(nsliy>0) { s.GetLine(strg, 255); SetSliY(nsliy); DBASSERT (nsliy==NSliY()); for(j=0;jRead(s); } // Lecture des bandes if( nbanx>0 ) { s.GetLine(strg, 255); for( j=0; jRead(s); } } if( nbany>0 ) { s.GetLine(strg, 255); for( j=0; jRead(s); } } return; }