Changeset 914 in Sophya for trunk/SophyaLib/NTools
- Timestamp:
- Apr 13, 2000, 6:04:50 PM (25 years ago)
- Location:
- trunk/SophyaLib/NTools
- Files:
-
- 4 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/SophyaLib/NTools/generaldata.cc
r514 r914 19 19 //================================================================ 20 20 21 //++ 22 // Class GeneralFitData 23 // Lib Outils++ 24 // include generaldata.h 25 // 26 // Classe de stoquage de donnees a plusieurs variables avec erreur 27 // sur l'ordonnee et sur les abscisses (options). 28 //| {x0(i),Ex0(i), x1(i),Ex1(i), x2(i),Ex2(i) ... ; Y(i),EY(i)} 29 //-- 30 31 // Pour memoire, structure du rangement (n=mNVar): 32 // - Valeur des abscisses mXP (idem pour mErrXP): 33 // x0,x1,x2,...,xn x0,x1,x2,...,xn .... x0,x1,x2,....,xn 34 // | 1er point | | 2sd point | .... | point mNData | 35 // Donc abscisse J=[0,mNVar[ du point numero I=[0,mNData[: mXP[I*mNVar+J] 36 // - Valeur de l'ordonnee mF (idem pour mErr et mOK): 37 // f f f 38 // | 1er point | | 2sd point | .... | point mNData | 39 // Donc point numero I [0,mNData[ : mF[i] 40 41 ////////////////////////////////////////////////////////////////////// 42 //++ 21 ////////////////////////////////////////////////////////////////////// 22 /*! 23 Constructeur. ``nVar'' represente la dimension de l'espace des abscisses, 24 ``ndatalloc'' le nombre maximum de points et ``errx'' si non nul 25 indique que l'on fournit des erreurs sur les ``nVar'' variables en abscisse. 26 */ 43 27 GeneralFitData::GeneralFitData(unsigned int nVar, unsigned int ndatalloc, uint_2 errx) 44 //45 // Constructeur. ``nVar'' represente la dimension de l'espace des abscisses,46 // ``ndatalloc'' le nombre maximum de points et ``errx'' si non nul47 // indique que l'on fournit des erreurs sur les ``nVar'' variables en abscisse.48 //--49 28 : mNVar(0), mNDataAlloc(0), mNData(0), mNDataGood(0), mOk_EXP(0) 50 29 , mXP(NULL), mErrXP(NULL), mF(NULL), mErr(NULL), mOK(NULL) … … 59 38 } 60 39 61 //++ 40 /*! 41 Constructeur par copie. Si ``clean'' est ``true'' 42 seules les donnees valides de ``data'' sont copiees. 43 Si ``clean'' est ``false'' (defaut) toutes les donnees 44 sont copiees et la taille totale de ``data'' est allouee 45 meme si elle est plus grande que la taille des donnees stoquees. 46 */ 62 47 GeneralFitData::GeneralFitData(const GeneralFitData& data, bool clean) 63 //64 // Constructeur par copie. Si ``clean'' est ``true''65 // seules les donnees valides de ``data'' sont copiees.66 // Si ``clean'' est ``false'' (defaut) toutes les donnees67 // sont copiees et la taille totale de ``data'' est allouee68 // meme si elle est plus grande que la taille des donnees stoquees.69 //--70 48 : mNVar(0), mNDataAlloc(0), mNData(0), mNDataGood(0), mOk_EXP(0) 71 49 , mXP(NULL), mErrXP(NULL), mF(NULL), mErr(NULL), mOK(NULL) … … 98 76 } 99 77 100 //++ 78 /*! 79 Constructeur par defaut. 80 */ 101 81 GeneralFitData::GeneralFitData() 102 //103 // Constructeur par defaut.104 //--105 82 : mNVar(0), mNDataAlloc(0), mNData(0), mNDataGood(0), mOk_EXP(0) 106 83 , mXP(NULL), mErrXP(NULL), mF(NULL), mErr(NULL), mOK(NULL) … … 110 87 } 111 88 112 //++ 89 /*! 90 Destructeur 91 */ 113 92 GeneralFitData::~GeneralFitData() 114 //115 // Destructeur116 //--117 93 { 118 94 Delete(); … … 120 96 121 97 ////////////////////////////////////////////////////////////////////// 122 //++ 98 /*! 99 Pour redefinir la structure de donnees (ou la creer si on a utilise 100 le createur par defaut). Voir les explications des arguments 101 dans les commentaires du constructeur. Si ``errx''\<0 alors 102 la valeur prise est celle definie auparavent. 103 */ 123 104 void GeneralFitData::Alloc(unsigned int nVar, unsigned int ndatalloc, int_2 errx) 124 //125 // Pour redefinir la structure de donnees (ou la creer si on a utilise126 // le createur par defaut). Voir les explications des arguments127 // dans les commentaires du constructeur. Si ``errx''<0 alors128 // la valeur prise est celle definie auparavent.129 //--130 105 { 131 106 ASSERT( nVar>0 && ndatalloc>0 ); … … 151 126 152 127 ////////////////////////////////////////////////////////////////////// 128 /*! 129 Gestion des des-allocations 130 */ 153 131 void GeneralFitData::Delete() 154 132 { … … 163 141 164 142 ////////////////////////////////////////////////////////////////////// 165 //++ 143 /*! 144 Remise a zero de la structure pour nouveau remplissage (pas d'arg) 145 ou remise a la position ``ptr'' (si arg). Les donnees apres ``ptr'' 146 sont sur-ecrites. 147 */ 166 148 void GeneralFitData::SetDataPtr(int ptr) 167 //168 // Remise a zero de la structure pour nouveau remplissage (pas d'arg)169 // ou remise a la position ``ptr'' (si arg). Les donnees apres ``ptr''170 // sont sur-ecrites.171 //--172 149 { 173 150 ASSERT(ptr >= 0 && ptr < mNDataAlloc); … … 179 156 180 157 ////////////////////////////////////////////////////////////////////// 181 //++ 158 /*! 159 Pour tuer un point 160 */ 182 161 void GeneralFitData::KillData(int i) 183 //184 // Pour tuer un point185 //--186 162 { 187 163 ASSERT(i >= 0 && i < mNData); … … 192 168 } 193 169 194 //++ 170 /*! 171 Pour tuer une serie de points 172 */ 195 173 void GeneralFitData::KillData(int i1,int i2) 196 //197 // Pour tuer une serie de points198 //--199 174 { 200 175 ASSERT(i1 >= 0 && i1 < mNData); … … 206 181 207 182 ////////////////////////////////////////////////////////////////////// 208 //++ 183 /*! 184 Pour re-valider le point numero i ([0,NData]). 185 */ 209 186 void GeneralFitData::ValidData(int i) 210 //211 // Pour re-valider le point numero i ([0,NData]).212 //--213 187 { 214 188 ASSERT(i >= 0 && i < mNData); … … 223 197 } 224 198 225 //++ 199 /*! 200 Pour re-valider les points numeros i1 a i2. 201 */ 226 202 void GeneralFitData::ValidData(int i1,int i2) 227 //228 // Pour re-valider les points numeros i1 a i2.229 //--230 203 { 231 204 ASSERT(i1 >= 0 && i1 < mNData); … … 236 209 } 237 210 238 //++ 211 /*! 212 Pour re-valider tous les points. 213 */ 239 214 void GeneralFitData::ValidData() 240 //241 // Pour re-valider tous les points.242 //--243 215 { 244 216 for(int i=0;i<mNData;i++) ValidData(i); … … 246 218 247 219 ////////////////////////////////////////////////////////////////////// 248 //++ 220 /*! 221 Pour redefinir un point a \f$ {x,[errx] ; f,err} \f$ 222 */ 249 223 void GeneralFitData::RedefineData1(int i,double x,double f,double err,double errx) 250 //251 // Pour redefinir un point a252 //| {x,[errx] ; f,err}253 //--254 224 { 255 225 RedefineData(i,&x,f,err,&errx); 256 226 } 257 227 258 //++ 228 /*! 229 Pour redefinir un point a \f$ {x,[errx], y,[erry] ; f,err} \f$ 230 */ 259 231 void GeneralFitData::RedefineData2(int i,double x,double y,double f 260 232 ,double err,double errx,double erry) 261 //262 // Pour redefinir un point a263 //| {x,[errx], y,[erry] ; f,err}264 //--265 233 { 266 234 double xp[2] = {x,y}; … … 269 237 } 270 238 271 //++ 239 /*! 240 Pour redefinir un point a 241 \f$ {xp[0],[errxp[0]], xp[1],[errxp[1]], xp[2],[errxp[2]],... ; f,err} \f$ 242 */ 272 243 void GeneralFitData::RedefineData(int i,double* xp,double f,double err,double* errxp) 273 //274 // Pour redefinir un point a275 //| {xp[0],[errxp[0]], xp[1],[errxp[1]], xp[2],[errxp[2]],... ; f,err}276 //--277 244 { 278 245 ASSERT(i>=0 && i<mNData); … … 300 267 301 268 ////////////////////////////////////////////////////////////////////// 302 //++ 269 /*! 270 Pour ajouter un point \f$ {x,[errx] ; f,err} \f$ 271 */ 303 272 void GeneralFitData::AddData1(double x, double f, double err, double errx) 304 //305 // Pour ajouter un point306 //| {x,[errx] ; f,err}307 //--308 273 { 309 274 AddData(&x,f,err,&errx); 310 275 } 311 276 312 //++ 277 /*! 278 Pour ajouter un point \f$ {x,[errx], y,[erry] ; f,err} \f$ 279 */ 313 280 void GeneralFitData::AddData2(double x, double y, double f 314 281 , double err, double errx, double erry) 315 //316 // Pour ajouter un point317 //| {x,[errx], y,[erry] ; f,err}318 //--319 282 { 320 283 double xp[2] = {x,y}; … … 323 286 } 324 287 325 //++ 288 /*! 289 Pour ajouter un point 290 \f$ {xp[0],[errxp[0]], xp[1],[errxp[1]], xp[2],[errxp[2]],... ; f,err} \f$ 291 */ 326 292 void GeneralFitData::AddData(double* xp, double f, double err,double* errxp) 327 //328 // Pour ajouter un point329 //| {xp[0],[errxp[0]], xp[1],[errxp[1]], xp[2],[errxp[2]],... ; f,err}330 //--331 293 { 332 294 ASSERT(mNData < mNDataAlloc); … … 351 313 } 352 314 353 //++ 315 /*! 316 Pour ajouter un point 317 \f$ {xp[0],[errxp[0]], xp[1],[errxp[1]], xp[2],[errxp[2]],... ; f,err} \f$ 318 */ 354 319 void GeneralFitData::AddData(float* xp, float f, float err, float* errxp) 355 //356 // Pour ajouter un point357 //| {xp[0],[errxp[0]], xp[1],[errxp[1]], xp[2],[errxp[2]],... ; f,err}358 //--359 320 { 360 321 {for(int i=0;i<mNVar;i++) BuffVar[i] = (double) xp[i];} … … 364 325 365 326 ////////////////////////////////////////////////////////////////////// 366 //++ 327 /*! 328 Pour remplir la structure de donnees d'un seul coup avec 329 \f$ {x(i),[errx(i)] ; f(i),err(i)} \f$ 330 */ 367 331 void GeneralFitData::SetData1(int nData 368 332 , double* x, double* f, double *err, double *errx) 369 //370 // Pour remplir la structure de donnees d'un seul coup avec371 //| {x(i),[errx(i)] ; f(i),err(i)}372 //--373 333 { 374 334 ASSERT(nData>0 && mNData+nData<=mNDataAlloc); … … 381 341 } 382 342 383 //++ 343 /*! 344 Pour remplir la structure de donnees d'un seul coup avec 345 \f$ {x(i),[errx(i)] ; f(i),err(i)} \f$ 346 */ 384 347 void GeneralFitData::SetData1(int nData 385 348 , float* x, float* f, float* err, float *errx) 386 //387 // Pour remplir la structure de donnees d'un seul coup avec388 //| {x(i),[errx(i)] ; f(i),err(i)}389 //--390 349 { 391 350 ASSERT(nData>0 && mNData+nData<=mNDataAlloc); … … 398 357 } 399 358 400 //++ 359 /*! 360 Pour remplir la structure de donnees d'un seul coup avec 361 \f$ {x(i),[errx(i)], y(i),[erry(i)], ; f(i),err(i)} \f$ 362 */ 401 363 void GeneralFitData::SetData2(int nData, double* x, double* y, double* f 402 364 ,double *err,double *errx,double *erry) 403 //404 // Pour remplir la structure de donnees d'un seul coup avec405 //| {x(i),[errx(i)], y(i),[erry(i)], ; f(i),err(i)}406 //--407 365 { 408 366 ASSERT(nData>0 && mNData+nData<=mNDataAlloc); … … 416 374 } 417 375 418 //++ 376 /*! 377 Pour remplir la structure de donnees d'un seul coup avec 378 \f$ {x(i),[errx(i)], y(i),[erry(i)], ; f(i),err(i)} \f$ 379 */ 419 380 void GeneralFitData::SetData2(int nData, float* x, float* y, float* f 420 381 ,float *err,float *errx,float *erry) 421 //422 // Pour remplir la structure de donnees d'un seul coup avec423 //| {x(i),[errx(i)], y(i),[erry(i)], ; f(i),err(i)}424 //--425 382 { 426 383 ASSERT(nData>0 && mNData+nData<=mNDataAlloc); … … 434 391 } 435 392 436 //++ 393 /*! 394 Pour remplir la structure de donnees d'un seul coup avec 395 \f$ {X0(i),[EX0(i)], X1(i),[EX1(i)], X2(i),[EX2(i)], ... ; F(i),Err(i)} \f$ 396 397 Attention: si la structure est n'est pas vide, les tableaux sont copies 398 apres les donnees pre-existantes (qui ne sont donc pas detruites). Pour 399 effacer les donnees pre-existantes utiliser SetDataPtr(0). 400 \verbatim 401 Ici **xp est un pointeur sur un tableau de pointeurs tq 402 xp[0] = &X0[0], xp[1] = &X1[0], xp[2] = &X2[0] ... 403 ou X0,X1,X2,... sont les tableaux X0[nData] X1[nData] X2[nData] ... 404 des variables (meme commentaire pour errxp). 405 \endverbatim 406 */ 437 407 void GeneralFitData::SetData(int nData,double** xp, double *f 438 408 , double *err, double** errxp) 439 //440 // Pour remplir la structure de donnees d'un seul coup avec441 //| {X0(i),[EX0(i)], X1(i),[EX1(i)], X2(i),[EX2(i)], ... ; F(i),Err(i)}442 // Attention: si la structure est n'est pas vide, les tableaux sont copies443 // apres les donnees pre-existantes (qui ne sont donc pas detruites). Pour444 // effacer les donnees pre-existantes utiliser SetDataPtr(0).445 //| Ici **xp est un pointeur sur un tableau de pointeurs tq446 //| xp[0] = &X0[0], xp[1] = &X1[0], xp[2] = &X2[0] ...447 //| ou X0,X1,X2,... sont les tableaux X0[nData] X1[nData] X2[nData] ...448 //| des variables (meme commentaire pour errxp).449 //--450 409 { 451 410 ASSERT(nData>0 && mNData+nData<=mNDataAlloc); … … 461 420 } 462 421 463 //++ 422 /*! 423 Voir commentaire ci-dessus. 424 */ 464 425 void GeneralFitData::SetData(int nData,float** xp, float *f 465 426 , float *err, float** errxp) 466 //467 // Voir commentaire ci-dessus.468 //--469 427 { 470 428 ASSERT(nData>0 && mNData+nData<=mNDataAlloc); … … 482 440 483 441 ////////////////////////////////////////////////////////////////////// 484 //++ 442 /*! 443 Impression de l'etat de la structure de donnees 444 */ 485 445 void GeneralFitData::PrintStatus() 486 //487 // Impression de l'etat de la structure de donnees488 //--489 446 { 490 447 cout<<"GeneralFitData:: "<<endl … … 495 452 } 496 453 497 //++ 454 /*! 455 Impression du point i 456 */ 498 457 void GeneralFitData::PrintData(int i) 499 //500 // Impression du point i501 //--502 458 { 503 459 ASSERT(i>=0 && i<mNData); … … 512 468 } 513 469 514 //++ 470 /*! 471 Impression des points i1 a i2 472 */ 515 473 void GeneralFitData::PrintData(int i1,int i2) 516 //517 // Impression des points i1 a i2518 //--519 474 { 520 475 if(i1<0) i1=0; … … 529 484 } 530 485 531 //++ 486 /*! 487 Impression de tous les points 488 */ 532 489 void GeneralFitData::PrintData() 533 //534 // Impression de tous les points535 //--536 490 { 537 491 ASSERT(mNData>0); … … 540 494 } 541 495 542 //++ 496 /*! 497 Impression de l'etat de la structure de donnees avec bornes sur "s" 498 */ 543 499 void GeneralFitData::Show(ostream& os) const 544 //545 // Impression de l'etat de la structure de donnees avec bornes sur "s"546 //--547 500 { 548 501 double min,max; … … 557 510 558 511 ////////////////////////////////////////////////////////////////////// 559 //++ 512 /*! 513 Retourne les numeros des points de valeurs minimum et maximum 514 de la variable ``var'': 515 \verbatim 516 La variable "var" est de la forme : var = AB avec 517 B = 0 : variable d'ordonnee Y (valeur de A indifferente) 518 B = 1 : erreur variable d'ordonnee EY (valeur de A indifferente) 519 B = 2 : variable d'abscisse X numero A #[0,NVar[ 520 B = 3 : erreur variable d'abscisse EX numero A #[0,NVar[ 521 - Return NData checked si ok, -1 si probleme. 522 \endverbatim 523 */ 560 524 int GeneralFitData::GetMnMx(int var,int& imin,int& imax) const 561 //562 // Retourne les numeros des points de valeurs minimum et maximum563 // de la variable ``var'':564 //| La variable "var" est de la forme : var = AB avec565 //| B = 0 : variable d'ordonnee Y (valeur de A indifferente)566 //| B = 1 : erreur variable d'ordonnee EY (valeur de A indifferente)567 //| B = 2 : variable d'abscisse X numero A #[0,NVar[568 //| B = 3 : erreur variable d'abscisse EX numero A #[0,NVar[569 //| - Return NData checked si ok, -1 si probleme.570 //--571 525 { 572 526 imin = imax = -1; … … 592 546 } 593 547 594 //++ 548 /*! 549 Retourne le minimum et le maximum de la variable ``var'' 550 (cf commentaires GetMnMx). 551 */ 595 552 int GeneralFitData::GetMnMx(int var,double& min,double& max) const 596 //597 // Retourne le minimum et le maximum de la variable ``var''598 // (cf commentaires GetMnMx).599 //--600 553 { 601 554 min = 1.; max = -1.; … … 622 575 623 576 ////////////////////////////////////////////////////////////////////// 624 //++ 577 /*! 578 // 579 Retourne la moyenne et le sigma de la variable ``var'' 580 (cf commentaires GetMnMx). 581 \verbatim 582 - Return : nombre de donnees utilisees, -1 si pb, -2 si sigma<0. 583 - Seuls les points valides de valeur entre min,max sont utilises. 584 Si min>=max pas de coupures sur les valeurs. 585 \endverbatim 586 */ 625 587 int GeneralFitData::GetMeanSigma(int var,double& mean,double& sigma,double min,double max) 626 //627 // Retourne la moyenne et le sigma de la variable ``var''628 // (cf commentaires GetMnMx).629 //| - Return : nombre de donnees utilisees, -1 si pb, -2 si sigma<0.630 //| - Seuls les points valides de valeur entre min,max sont utilises.631 //| Si min>=max pas de coupures sur les valeurs.632 //--633 588 { 634 589 mean = sigma = 0.; … … 661 616 } 662 617 663 //++ 618 /*! 619 Retourne le mode de la variable ``var'' 620 (cf commentaires GetMnMx). 621 \verbatim 622 - Return : nombre de donnees utilisees, -1 si pb. 623 - Seuls les points valides de valeur entre min,max sont utilises. 624 Si min>=max pas de coupures sur les valeurs. 625 - Le calcul du mode est approximee par la formule: 626 Mode = Median - coeff*(Mean-Median) (def: coeff=0.8) 627 - Kendall and Stuart donne coeff=2., mais coeff peut etre regle. 628 \endverbatim 629 */ 664 630 int GeneralFitData::GetMoMeMed(int var,double& mode,double& mean,double& median, 665 631 double min,double max,double coeff) 666 //667 // Retourne le mode de la variable ``var''668 // (cf commentaires GetMnMx).669 //| - Return : nombre de donnees utilisees, -1 si pb.670 //| - Seuls les points valides de valeur entre min,max sont utilises.671 //| Si min>=max pas de coupures sur les valeurs.672 //| - Le calcul du mode est approximee par la formule:673 //| Mode = Median - coeff*(Mean-Median) (def: coeff=0.8)674 //| - Kendall and Stuart donne coeff=2., mais coeff peut etre regle.675 //--676 632 { 677 633 mode = mean = median = 0.; … … 716 672 } 717 673 718 //++ 674 /*! 675 Cf description ci-dessus ``GetMoMeMed''. 676 */ 719 677 int GeneralFitData::GetMode(int var,double& mode,double min,double max,double coeff) 720 //721 // Cf description ci-dessus ``GetMoMeMed''.722 //--723 678 { 724 679 double mean,median; … … 727 682 728 683 ////////////////////////////////////////////////////////////////////// 729 //++ 684 /*! 685 Pour fiter un polynome de degre ``degre''. On fite 686 Y=f(X) ou Y=Val et X=Absc(varx). Si ``ey'' est ``true'' 687 le fit prend en compte les erreurs stoquees dans EVal, 688 sinon fit sans erreurs. Le resultat du fit est retourne 689 dans le polynome ``pol''. 690 \verbatim 691 Return: 692 - Res = le residu du fit 693 - -1 si degre<0 694 - -2 si probleme sur numero de variable X 695 - -4 si NDataGood<0 696 - -5 si nombre de data trouves different de NDataGood 697 \endverbatim 698 */ 730 699 double GeneralFitData::PolFit(int varx,Poly& pol,int degre,bool ey) 731 //732 // Pour fiter un polynome de degre ``degre''. On fite733 // Y=f(X) ou Y=Val et X=Absc(varx). Si ``ey'' est ``true''734 // le fit prend en compte les erreurs stoquees dans EVal,735 // sinon fit sans erreurs. Le resultat du fit est retourne736 // dans le polynome ``pol''.737 //| Return:738 //| - Res = le residu du fit739 //| - -1 si degre<0740 //| - -2 si probleme sur numero de variable X741 //| - -4 si NDataGood<0742 //| - -5 si nombre de data trouves different de NDataGood743 //--744 700 { 745 701 if(degre<0) return -1.; … … 769 725 } 770 726 771 //++ 727 /*! 728 Pour fiter un polynome de degre ``degre1''. On fite 729 Z=f(X,Y) ou Z=Val et X=Absc(varx) et Y=Absc(vary). 730 Si ``ey'' est ``true'' le fit prend en compte les erreurs 731 stoquees dans EVal, sinon fit sans erreurs. Si ``degre2'' 732 negatif, le fit determine un polynome en X,Y de degre 733 total ``degre`''. Si ``degre2'' positif ou nul, le fit 734 demande un fit de ``degre1'' pour la variable X et de degre 735 ``degre2'' sur la variable Y. Le resultat du fit est retourne 736 dans le polynome ``pol''. 737 \verbatim 738 Return: 739 - Res = le residu du fit 740 - -1 si degre<0 741 - -2 si probleme sur numero de variable X 742 - -3 si probleme sur numero de variable Y 743 - -4 si NDataGood<0 744 - -5 si nombre de data trouves different de NDataGood 745 \endverbatim 746 */ 772 747 double GeneralFitData::PolFit(int varx,int vary,Poly2& pol,int degre1,int degre2,bool ez) 773 //774 //775 // Pour fiter un polynome de degre ``degre1''. On fite776 // Z=f(X,Y) ou Z=Val et X=Absc(varx) et Y=Absc(vary).777 // Si ``ey'' est ``true'' le fit prend en compte les erreurs778 // stoquees dans EVal, sinon fit sans erreurs. Si ``degre2''779 // negatif, le fit determine un polynome en X,Y de degre780 // total ``degre`''. Si ``degre2'' positif ou nul, le fit781 // demande un fit de ``degre1'' pour la variable X et de degre782 // ``degre2'' sur la variable Y. Le resultat du fit est retourne783 // dans le polynome ``pol''.784 //| Return:785 //| - Res = le residu du fit786 //| - -1 si degre<0787 //| - -2 si probleme sur numero de variable X788 //| - -3 si probleme sur numero de variable Y789 //| - -4 si NDataGood<0790 //| - -5 si nombre de data trouves different de NDataGood791 //--792 748 { 793 749 if(degre1<0) return -1.; … … 823 779 824 780 ////////////////////////////////////////////////////////////////////// 825 //++ 781 /*! 782 Retourne une classe contenant les residus du fit ``gfit''. 783 */ 826 784 GeneralFitData GeneralFitData::FitResidus(GeneralFit& gfit) 827 //828 // Retourne une classe contenant les residus du fit ``gfit''.829 //--830 785 { 831 786 if(gfit.GetNVar()!=mNVar) … … 834 789 } 835 790 836 //++ 791 /*! 792 Retourne une classe contenant la function du fit ``gfit''. 793 */ 837 794 GeneralFitData GeneralFitData::FitFunction(GeneralFit& gfit) 838 //839 // Retourne une classe contenant la function du fit ``gfit''.840 //--841 795 { 842 796 if(gfit.GetNVar()!=mNVar) … … 846 800 847 801 ////////////////////////////////////////////////////////////////////// 848 //++ 802 /*! 803 // 804 Retourne la donnee `n' dans le vecteur de double `ret'. 805 \verbatim 806 Par defaut, ret=NULL et le buffer interne de la classe est retourne 807 - Les donnees sont rangees dans l'ordre: 808 x0,x1,x2,... ; ex0,ex1,ex2,... ; y ; ey ; ok(0/1) 809 |<- NVar ->| + |<- NVar ->| + 1 + 1 + 1 810 Le vecteur ret a la taille 2*NVar+2+1 811 \endverbatim 812 */ 849 813 r_8* GeneralFitData::GetVec(int n, r_8* ret) const 850 //851 // Retourne la donnee `n' dans le vecteur de double `ret'.852 //| Par defaut, ret=NULL et le buffer interne de la classe est retourne853 //| - Les donnees sont rangees dans l'ordre:854 //| x0,x1,x2,... ; ex0,ex1,ex2,... ; y ; ey ; ok(0/1)855 //| |<- NVar ->| + |<- NVar ->| + 1 + 1 + 1856 //| Le vecteur ret a la taille 2*NVar+2+1857 //--858 814 { 859 815 int i; … … 870 826 } 871 827 872 //++ 828 /*! 829 Retourne la donnee `n' dans le vecteur de float `ret' 830 (meme commentaires que pour GetVec). 831 */ 873 832 r_4* GeneralFitData::GetVecR4(int n, r_4* ret) const 874 //875 // Retourne la donnee `n' dans le vecteur de float `ret'876 // (meme commentaires que pour GetVec).877 //--878 833 { 879 834 if (ret == NULL) ret = BuffVarR4; … … 886 841 887 842 ////////////////////////////////////////////////////////////////////// 888 //++889 // int inline int GetSpaceFree() const890 // Retourne la place restante dans la structure (nombre de891 // donnees que l'on peut encore stoquer).892 //--893 //++894 // inline int NVar() const895 // Retourne le nombre de variables Xi896 //--897 //++898 // inline int NData()899 // Retourne le nombre de donnees900 //--901 //++902 // inline int NDataGood() const903 // Retourne le nombre de bonnes donnees (utilisees pour le fit)904 //--905 //++906 // inline int NDataAlloc() const907 // Retourne la place maximale allouee pour les donnees908 //--909 //++910 // inline unsigned short int IsValid(int i) const911 // Retourne 1 si point valide, sinon 0912 //--913 //++914 // inline bool HasXErrors()915 // Retourne ``true'' si il y a des erreurs sur les variables916 // d'abscisse, ``false'' sinon.917 //--918 //++919 // inline double X1(int i) const920 // Retourne l'abscisse pour 1 dimension (y=f(x)) donnee I921 //--922 //++923 // inline double X(int i) const924 // Retourne la 1er abscisse (X) pour (v=f(x,y,z,...)) donnee I925 //--926 //++927 // inline double Y(int i) const928 // Retourne la 2sd abscisse (Y) pour (v=f(x,y,z,...)) donnee I929 //--930 //++931 // inline double Z(int i) const932 // Retourne la 3ieme abscisse (Z) pour (v=f(x,y,z,...)) donnee I933 //--934 //++935 // inline double Absc(int j,int i) const936 // Retourne la Jieme abscisse (Xj) pour (v=f(x0,x1,x2,...)) donnee I937 //--938 //++939 // inline double Val(int i) const940 // Retourne la valeur de la Ieme donnee941 //--942 //++943 // inline double EX1(int i) const944 // Retourne l'erreur (dx) sur l'abscisse pour 1 dimension (y=f(x)) donnee I945 //--946 //++947 // inline double EX(int i) const948 // Retourne l'erreur (dx) sur la 1er abscisse (X) pour (v=f(x,y,z,...)) donnee I949 //--950 //++951 // inline double EY(int i) const952 // Retourne l'erreur (dy) sur la 2sd abscisse (Y) pour (v=f(x,y,z,...)) donnee I953 //--954 //++955 // inline double EZ(int i) const956 // Retourne l'erreur (dz) sur la 3ieme abscisse (Z) pour (v=f(x,y,z,...)) donnee I957 //--958 //++959 // inline double EAbsc(int j,int i) const960 // Retourne l'erreur (dxj) sur la Jieme abscisse (Xj) pour (v=f(x0,x1,x2,...)) donnee I961 //--962 //++963 // inline double EVal(int i) const {return mErr[i];}964 // Retourne l'erreur de la Ieme donnee965 //--966 967 968 //////////////////////////////////////////////////////////////////////969 843 // ------- Implementation de l interface NTuple --------- 970 844 845 /*! 846 Retourne le nombre de ligne = NData() (pour interface NTuple) 847 */ 971 848 uint_4 GeneralFitData::NbLines() const 972 849 { … … 974 851 } 975 852 976 //++ 853 /*! 854 Retourne le nombre de colonnes du ntuple equivalent: 855 \verbatim 856 Exemple: on a une fonction sur un espace a 4 dimensions: 857 "x0,x1,x2,x3 , ex0,ex1,ex2,ex3 , y, ey , ok" 858 0 1 2 3 4 5 6 7 8 9 10 859 | | | | | | | 860 0 nv-1 nv 2*nv-1 2*nv 2*nv+1 2*nv+2 861 soit 2*nvar+3 variables/colonnes. 862 \endverbatim 863 (pour interface NTuple) 864 */ 977 865 uint_4 GeneralFitData::NbColumns() const 978 //979 // Retourne le nombre de colonnes du ntuple equivalent:980 //| Exemple: on a une fonction sur un espace a 4 dimensions:981 //| "x0,x1,x2,x3 , ex0,ex1,ex2,ex3 , y, ey , ok"982 //| 0 1 2 3 4 5 6 7 8 9 10983 //| | | | | | | |984 //| 0 nv-1 nv 2*nv-1 2*nv 2*nv+1 2*nv+2985 //| soit 2*nvar+3 variables/colonnes.986 //--987 866 { 988 867 return(2*NVar()+3); 989 868 } 990 869 870 //! Pour interface NTuple 991 871 r_8 * GeneralFitData::GetLineD(int n) const 992 872 { … … 994 874 } 995 875 876 //! Pour interface NTuple 996 877 r_8 GeneralFitData::GetCell(int n, int k) const 997 878 { … … 1001 882 } 1002 883 884 //! Pour interface NTuple 1003 885 r_8 GeneralFitData::GetCell(int n, string const & nom) const 1004 886 { … … 1007 889 } 1008 890 1009 //++ 891 /*! 892 Retourne le minimum et le maximum de la variable `k' (pour interface NTuple). 893 */ 1010 894 void GeneralFitData::GetMinMax(int k, double& min, double& max) const 1011 //1012 // Retourne le minimum et le maximum de la variable `k'.1013 //--1014 895 { 1015 896 int var; … … 1024 905 } 1025 906 907 //! Pour interface NTuple 1026 908 void GeneralFitData::GetMinMax(string const & nom, double& min, double& max) const 1027 909 { … … 1030 912 } 1031 913 914 //! Pour interface NTuple 1032 915 int GeneralFitData::ColumnIndex(string const & nom) const 1033 916 { … … 1043 926 } 1044 927 928 //! Pour interface NTuple 1045 929 string GeneralFitData::ColumnName(int k) const 1046 930 { … … 1056 940 } 1057 941 1058 //++ 942 /*! 943 Retourne une chaine de caracteres avec la declaration des noms de 944 variables. si "nomx!=NULL" , des instructions d'affectation 945 a partir d'un tableau "nomx[i]" sont ajoutees (pour interface NTuple). 946 */ 1059 947 string GeneralFitData::VarList_C(const char* nomx) const 1060 //1061 // Retourne une chaine de caracteres avec la declaration des noms de1062 // variables. si "nomx!=NULL" , des instructions d'affectation1063 // a partir d'un tableau "nomx[i]" sont ajoutees.1064 //--1065 948 { 1066 949 char buff[256]; -
trunk/SophyaLib/NTools/generaldata.h
r552 r914 19 19 //================================================================ 20 20 21 /*! 22 Classe de stoquage de donnees a plusieurs variables avec erreur 23 sur l'ordonnee et sur les abscisses (options) : 24 25 \f$ {x0(i),Ex0(i), x1(i),Ex1(i), x2(i),Ex2(i) ... ; Y(i),EY(i)} \f$ 26 \verbatim 27 Pour memoire, structure du rangement (n=mNVar): 28 - Valeur des abscisses mXP (idem pour mErrXP): 29 x0,x1,x2,...,xn x0,x1,x2,...,xn .... x0,x1,x2,....,xn 30 | 1er point | | 2sd point | .... | point mNData | 31 Donc abscisse J=[0,mNVar[ du point numero I=[0,mNData[: mXP[I*mNVar+J] 32 - Valeur de l'ordonnee mF (idem pour mErr et mOK): 33 f f f 34 | 1er point | | 2sd point | .... | point mNData | 35 Donc point numero I [0,mNData[ : mF[i] 36 \endverbatim 37 */ 38 21 39 class GeneralFitData : public AnyDataObj , public NTupleInterface { 22 40 friend class GeneralFit; 23 41 friend class ObjFileIO<GeneralFitData>; 24 42 public: 25 enum {Def_ErrF = 1, Def_ErrX = 0}; 43 //! Valeurs par defaut pour l'utilisation des erreurs 44 enum { 45 Def_ErrF = 1, //!< erreurs sur F par defaut 46 Def_ErrX = 0 //!< pas d'erreurs sur les variables X,Y,... par defaut 47 }; 26 48 27 49 GeneralFitData(unsigned int nVar, unsigned int nDataAlloc, uint_2 errx=0); … … 67 89 inline void Show() const {Show(cout);} 68 90 91 //! Retourne la place restante dans la structure (nombre de donnees que l'on peut encore stoquer). 69 92 inline int GetSpaceFree() const { return mNDataAlloc - mNData; } 93 //! Retourne le nombre de variables Xi 70 94 inline int NVar() const {return mNVar;} 95 //! Retourne le nombre de donnees 71 96 inline int NData() const {return mNData;} 97 //! Retourne le nombre de bonnes donnees (utilisees pour le fit) 72 98 inline int NDataGood() const {return mNDataGood;} 99 //! Retourne la place maximale allouee pour les donnees 73 100 inline int NDataAlloc() const {return mNDataAlloc;} 74 101 102 //! Retourne 1 si point valide, sinon 0 75 103 inline unsigned short int IsValid(int i) const 76 104 {if(i>=0 && i<mNData) return mOK[i]; else return 0;} 105 //! Retourne ``true'' si il y a des erreurs sur les variables d'abscisse, ``false'' sinon. 77 106 inline bool HasXErrors() {if(mErrXP) return true; else return false;} 78 107 108 //! Retourne l'abscisse pour 1 dimension (y=f(x)) donnee I 79 109 inline double X1(int i) const 80 110 {if(i>=0 && i<mNData) return mXP[i]; else return 0.;} 111 //! Retourne la 1er abscisse (X) pour (v=f(x,y,z,...)) donnee I 81 112 inline double X(int i) const 82 113 {if(i>=0 && i<mNData) return mXP[i*mNVar]; else return 0.;} 114 //! Retourne la 2sd abscisse (Y) pour (v=f(x,y,z,...)) donnee I 83 115 inline double Y(int i) const 84 116 {if(i>=0 && i<mNData && 1<mNVar) return mXP[i*mNVar+1]; else return 0.;} 117 //! etourne la 3ieme abscisse (Z) pour (v=f(x,y,z,...)) donnee I 85 118 inline double Z(int i) const 86 119 {if(i>=0 && i<mNData && 2<mNVar) return mXP[i*mNVar+2]; else return 0.;} 120 //! Retourne la Jieme abscisse (Xj) pour (v=f(x0,x1,x2,...)) donnee I 87 121 inline double Absc(int j,int i) const 88 122 {if(i>=0 && i<mNData && j<mNVar)return mXP[i*mNVar+j]; else return 0.;} 123 //! Retourne la valeur de la Ieme donnee 89 124 inline double Val(int i) const 90 125 {if(i>=0 && i<mNData) return mF[i]; else return 0.;} 91 126 127 //! Retourne l'erreur (dx) sur l'abscisse pour 1 dimension (y=f(x)) donnee I 92 128 inline double EX1(int i) const 93 129 {if(mErrXP && i>=0 && i<mNData) return mErrXP[i]; else return 0.;} 130 //! Retourne l'erreur (dx) sur la 1er abscisse (X) pour (v=f(x,y,z,...)) donnee I 94 131 inline double EX(int i) const 95 132 {if(mErrXP && i>=0 && i<mNData) return mErrXP[i*mNVar]; else return 0.;} 133 //! Retourne l'erreur (dy) sur la 2sd abscisse (Y) pour (v=f(x,y,z,...)) donnee I 96 134 inline double EY(int i) const 97 135 {if(mErrXP && i>=0 && i<mNData && 1<mNVar) return mErrXP[i*mNVar+1]; 98 136 else return 0.;} 137 //! Retourne l'erreur (dz) sur la 3ieme abscisse (Z) pour (v=f(x,y,z,...)) donnee I 99 138 inline double EZ(int i) const 100 139 {if(mErrXP && i>=0 && i<mNData && 2<mNVar) return mErrXP[i*mNVar+2]; 101 140 else return 0.;} 141 //! Retourne l'erreur (dxj) sur la Jieme abscisse (Xj) pour (v=f(x0,x1,x2,...)) donnee I 102 142 inline double EAbsc(int j,int i) const 103 143 {if(mErrXP && i>=0 && i<mNData && j<mNVar) return mErrXP[i*mNVar+j]; 104 144 else return 0.;} 145 //! Retourne l'erreur de la Ieme donnee 105 146 inline double EVal(int i) const 106 147 {if(i>=0 && i<mNData) return mErr[i]; else return 0.;} … … 139 180 int_4 mNDataGood; 140 181 uint_2 mOk_EXP; 141 r_8* mXP; // x0 y0 z0, x1 y1 z1, ..., xn yn zn142 r_8* mErrXP; // Ex0 Ey0 Ez0, Ex1 Ey1 Ez1, ..., Exn Eyn Ezn143 r_8* mF; // F0, F1, ...., Fn144 r_8* mErr; // EF0, EF1, ...., EFn145 uint_2* mOK; //1 si pt valid, 0 sinon182 r_8* mXP; //!< x0 y0 z0, x1 y1 z1, ..., xn yn zn 183 r_8* mErrXP; //!< Ex0 Ey0 Ez0, Ex1 Ey1 Ez1, ..., Exn Eyn Ezn 184 r_8* mF; //!< F0, F1, ...., Fn 185 r_8* mErr; //!< EF0, EF1, ...., EFn 186 uint_2* mOK; //!< 1 si pt valid, 0 sinon 146 187 r_8* BuffVar; 147 188 r_4* BuffVarR4; -
trunk/SophyaLib/NTools/generalfit.cc
r774 r914 21 21 //================================================================ 22 22 23 //++ 24 // Class GeneralFunction 25 // Lib Outils++ 26 // include generalfit.h 27 // 28 // Classe de fonctions parametrees a plusieurs variables. 29 //| F[x1,x2,x3,...:a1,a2,a3,...] 30 //-- 31 32 ////////////////////////////////////////////////////////////////////// 33 //++ 23 ////////////////////////////////////////////////////////////////////// 24 /*! 25 Creation d'une fonction de `nVar' variables et `nPar' parametres: 26 \f$ F[x(1),x(2),x(3),...x(nVar) : a(1),a(2),a(3),...,a(nPar)] \f$ 27 */ 34 28 GeneralFunction::GeneralFunction(unsigned int nVar, unsigned int nPar) 35 //36 // Creation d'une fonction de `nVar' variables et `nPar' parametres.37 //| F[x(1),x(2),x(3),...x(nVar) : a(1),a(2),a(3),...,a(nPar)]38 //--39 29 : mNVar(nVar), mNPar(nPar) 40 30 { … … 45 35 } 46 36 47 //++48 37 GeneralFunction::~GeneralFunction() 49 //50 //--51 38 { 52 39 delete[] deltaParm; … … 55 42 56 43 ////////////////////////////////////////////////////////////////////// 57 //++ 44 /*! 45 Valeur et Derivees de la fonction (fct virtuelle par defaut). 46 */ 58 47 double GeneralFunction::Val_Der(double const xp[], double const* parm 59 48 , double *DgDpar) 60 //61 // Valeur et Derivees de la fonction (fct virtuelle par defaut).62 //--63 49 { 64 50 for(int i=0;i<mNPar;i++) tmpParm[i] = parm[i]; … … 77 63 78 64 ////////////////////////////////////////////////////////////////////// 79 //++ 65 /*! 66 Definition de la variation du parametre numPar 67 pour calculer la derivee automatiquement. 68 */ 80 69 void GeneralFunction::SetDeltaParm(int numPar, double d) 81 //82 // Definition de la variation du parametre numPar83 // pour calculer la derivee automatiquement.84 //--85 70 { 86 71 ASSERT(numPar >= 0 && numPar < mNPar); … … 88 73 } 89 74 90 //++ 75 76 /*! 77 Idem precedente fonction mais pour tous les parametres 78 */ 91 79 void GeneralFunction::SetDeltaParm(double const* dparam) 92 //93 // Idem precedente fonction mais pour tous les parametres94 //--95 80 { 96 81 for(int i=0;i<mNPar;i++) deltaParm[i] = dparam[i]; 97 82 } 98 99 //////////////////////////////////////////////////////////////////////100 // Rappel des inline functions pour commentaires101 //++102 // virtual double Value(double const xp[], double const* parm)=0;103 // Valeur de la fonction a definir par l'utilisateur (fct virtuelle pure)104 //--105 //++106 // inline int NVar() const107 // Retourne le nombre de variables Xi108 //--109 //++110 // inline int NPar() const111 // Retourne le nombre de parametres Ai112 //--113 83 114 84 //================================================================ … … 116 86 //================================================================ 117 87 118 //++119 // Class GeneralFunc120 // Lib Outils++121 // include generalfit.h122 //123 // Classe de fonctions parametrees a plusieurs variables124 // derivant de ``GeneralFunction''. Permet de definir125 // une fonction a fiter sans passer par une classe derivee126 // en utilisant l'ecriture courante du C. La fonction127 // retournant les derivees par rapport aux parametres du fit128 // peut etre egalement fournie (optionnel).129 //--130 131 88 ///////////////////////////////////////////////////////////////// 132 //++ 133 GeneralFunc::GeneralFunc(unsigned int nvar, unsigned int npar, double (*fun) (double const*, double const*) 134 , double (*funder) (double const*, double const*, double*) ) 135 // 136 // Createur, on passe le nom ``fun'' de la fonction a la mode C. 137 // On peut optionellement egalement passer le nom de la fonction 138 // ``funder'' qui retourne les valeurs des derivees par rapport 139 // aux parametres du fit. 140 //-- 141 //++ 142 //| ---------------------- 143 //| Exemple d'utilisation: 144 //| ---------------------- 145 //| include "generalfit.h" 146 //| ... 147 //| double gaussc(double const* x,double const* p); 148 //| double d_gaussc(double const* x,double const* p,double* dp); 149 //| ... 150 //| main { 151 //| ... 152 //| // Fit SANS calcul automatique des derivees 153 //| GeneralFunc myfunc(2,7,gaussc); 154 //| GeneralFit myfit(&myfunc); 155 //| ... 156 //| myfit.Fit(); 157 //| ... 158 //| // Fit AVEC calcul automatique des derivees 159 //| GeneralFunc myfunc(2,7,gaussc,d_gaussc); 160 //| GeneralFit myfit(&myfunc); 161 //| ... 162 //| myfit.Fit(); 163 //| } 164 //-- 165 //++ 166 //| // Definition de la fonction a fitter a la mode C 167 //| double gaussc(double const* x,double const* p) 168 //| // Fonction: X=(x[0]-p[1])/p[3], Y=(x[1]-p[2])/p[4], 169 //| // f = p[0]*exp{-0.5*[X^2+Y^2-2*p[5]*X*Y]} + p[6] 170 //| { 171 //| double X = (x[0]-p[1])/p[3]; 172 //| double Y = (x[1]-p[2])/p[4]; 173 //| return p[0]*exp(-(X*X+Y*Y-2*p[5]*X*Y)/2)+p[6]; 174 //| } 175 //| // Definition de la fonction des derivees / parametres 176 //| // Cette fonction retourne aussi la valeur de la fonction a fitter. 177 //| double d_gaussc(double const* x,double const* p,double* dp) 178 //| { 179 //| dp[0] = derivee de gaussc par rapport au parametre p[0] 180 //| ... 181 //| dp[6] = derivee de gaussc par rapport au parametre p[6] 182 //| return gaussc(x,p); 183 //| } 184 //-- 89 /*! 90 Createur, on passe le nom ``fun'' de la fonction a la mode C. 91 On peut optionellement egalement passer le nom de la fonction 92 ``funder'' qui retourne les valeurs des derivees par rapport 93 aux parametres du fit. 94 \verbatim 95 ---------------------- 96 Exemple d'utilisation: 97 ---------------------- 98 include "generalfit.h" 99 ... 100 double gaussc(double const* x,double const* p); 101 double d_gaussc(double const* x,double const* p,double* dp); 102 ... 103 main { 104 ... 105 // Fit SANS calcul automatique des derivees 106 GeneralFunc myfunc(2,7,gaussc); 107 GeneralFit myfit(&myfunc); 108 ... 109 myfit.Fit(); 110 ... 111 // Fit AVEC calcul automatique des derivees 112 GeneralFunc myfunc(2,7,gaussc,d_gaussc); 113 GeneralFit myfit(&myfunc); 114 ... 115 myfit.Fit(); 116 } 117 // Definition de la fonction a fitter a la mode C 118 double gaussc(double const* x,double const* p) 119 // Fonction: X=(x[0]-p[1])/p[3], Y=(x[1]-p[2])/p[4], 120 // f = p[0]*exp{-0.5*[X^2+Y^2-2*p[5]*X*Y]} + p[6] 121 { 122 double X = (x[0]-p[1])/p[3]; 123 double Y = (x[1]-p[2])/p[4]; 124 return p[0]*exp(-(X*X+Y*Y-2*p[5]*X*Y)/2)+p[6]; 125 } 126 // Definition de la fonction des derivees / parametres 127 // Cette fonction retourne aussi la valeur de la fonction a fitter. 128 double d_gaussc(double const* x,double const* p,double* dp) 129 { 130 dp[0] = derivee de gaussc par rapport au parametre p[0] 131 ... 132 dp[6] = derivee de gaussc par rapport au parametre p[6] 133 return gaussc(x,p); 134 } 135 \endverbatim 136 */ 137 GeneralFunc::GeneralFunc(unsigned int nvar, unsigned int npar 138 , double (*fun) (double const*, double const*) 139 , double (*funder) (double const*, double const*, double*) ) 185 140 : GeneralFunction(nvar,npar), tmpFun(fun), tmpFunDer(funder) 186 141 { … … 206 161 //================================================================ 207 162 208 //++ 209 // Class GeneralXi2 210 // Lib Outils++ 211 // include generalfit.h 163 ////////////////////////////////////////////////////////////////////// 164 /*! 212 165 // 213 // Classe de Xi2 a plusieurs parametres. 214 //| Xi2[a1,a2,a3,...] 215 //-- 216 217 ////////////////////////////////////////////////////////////////////// 218 //++ 166 Creation d'un Xi2 de `nPar' parametres. 167 \f$ Xi2[a(1),a(2),a(3),...,a(nPar)] \f$ 168 */ 219 169 GeneralXi2::GeneralXi2(unsigned int nPar) 220 //221 // Creation d'un Xi2 de `nPar' parametres.222 //| Xi2[a(1),a(2),a(3),...,a(nPar)]223 //--224 170 : mNPar(nPar) 225 171 { … … 229 175 } 230 176 231 //++232 177 GeneralXi2::~GeneralXi2() 233 //234 //--235 178 { 236 179 delete[] deltaParm; … … 238 181 239 182 ////////////////////////////////////////////////////////////////////// 240 //++ 183 /*! 184 Derivee du Xi2 par rapport au parametre `i' 185 pour les valeurs `parm' des parametres. 186 */ 241 187 double GeneralXi2::Derivee(GeneralFitData& data, int i, double* parm) 242 //243 // Derivee du Xi2 par rapport au parametre `i'244 // pour les valeurs `parm' des parametres.245 //--246 188 { 247 189 int dum; … … 255 197 } 256 198 257 //++ 199 /*! 200 Derivee seconde du Xi2 par rapport aux parametres `i' et `j' 201 pour les valeurs `parm' des parametres. Attention, cette fonction 202 calcule d/di(dC2/dj), valeur qui est numeriquement differente 203 de d/dj(dC2/di). 204 \verbatim 205 206 **** Remarque: Derivee2 = dXi2/dPi.dPj represente le Hessien. 207 Derivee2(k,l)= dXi2/dPk.dPl 208 = 2*SUMi{1/Si^2*[df(xi;P)/dPk * df(xi;P)/dPl] 209 + [yi-f(xi;P)] * df(xi;P)/dPk.dPl } 210 ou (xi,yi) sont les points de mesure. "Si" l'erreur sur le point i 211 SUMi represente la somme sur les points de mesure 212 f(x;P) represente le modele parametrique a fitter 213 "P" represente l'ensemble des parametres et "Pi" le ieme parametre 214 Les composantes du Hessien dependent des derivees 1ere et 2sd du modele 215 a fitter f(x;P) selon les parametres "Pi". La prise en compte des derivees 216 secondes est un facteur destabilisant. De plus le facteur [yi-f(xi;P)] 217 devant la derivee 2sd est seulement l'erreur de mesure aleatoire qui 218 n'est pas correlee avec le modele. Le terme avec la derivee 2sd 219 tend donc a s'annuler et peut donc etre omis. 220 (cf. Numerical Recipes in C, chap 15 Modeling of Data, Nonlinear Models, 221 Calculation of the Gradient and Hessian p682,683) 222 223 **** Conseil: Il est conseille a l'utilisateur de sur-ecrire 224 la fonction virtuelle Derivee2 et de la remplacer par: 225 Derivee2(k,l) = 2*SUMi{1/Si^2*[df(xi;P)/dPk * df(xi;P)/dPl]} 226 \endverbatim 227 */ 258 228 double GeneralXi2::Derivee2(GeneralFitData& data, int i, int j, double* parm) 259 //260 // Derivee seconde du Xi2 par rapport aux parametres `i' et `j'261 // pour les valeurs `parm' des parametres. Attention, cette fonction262 // calcule d/di(dC2/dj), valeur qui est numeriquement differente263 // de d/dj(dC2/di).264 //--265 //++266 //|267 //| **** Remarque: Derivee2 = dXi2/dPi.dPj represente le Hessien.268 //| Derivee2(k,l)= dXi2/dPk.dPl269 //| = 2*SUMi{1/Si^2*[df(xi;P)/dPk * df(xi;P)/dPl]270 //| + [yi-f(xi;P)] * df(xi;P)/dPk.dPl }271 //| ou (xi,yi) sont les points de mesure. "Si" l'erreur sur le point i272 //| SUMi represente la somme sur les points de mesure273 //| f(x;P) represente le modele parametrique a fitter274 //| "P" represente l'ensemble des parametres et "Pi" le ieme parametre275 //| Les composantes du Hessien dependent des derivees 1ere et 2sd du modele276 //| a fitter f(x;P) selon les parametres "Pi". La prise en compte des derivees277 //| secondes est un facteur destabilisant. De plus le facteur [yi-f(xi;P)]278 //| devant la derivee 2sd est seulement l'erreur de mesure aleatoire qui279 //| n'est pas correlee avec le modele. Le terme avec la derivee 2sd280 //| tend donc a s'annuler et peut donc etre omis.281 //| (cf. Numerical Recipes in C, chap 15 Modeling of Data, Nonlinear Models,282 //| Calculation of the Gradient and Hessian p682,683)283 //|284 //| **** Conseil: Il est conseille a l'utilisateur de sur-ecrire285 //| la fonction virtuelle Derivee2 et de la remplacer par:286 //| Derivee2(k,l) = 2*SUMi{1/Si^2*[df(xi;P)/dPk * df(xi;P)/dPl]}287 //--288 229 { 289 230 double d = deltaParm[i]; … … 298 239 299 240 ////////////////////////////////////////////////////////////////////// 300 //++ 241 /*! 242 Definition de la variation 'd' du parametre 'numPar' 243 pour calculer la derivee automatiquement. 244 */ 301 245 void GeneralXi2::SetDeltaParm(int numPar, double d) 302 //303 // Definition de la variation du parametre numPar304 // pour calculer la derivee automatiquement.305 //--306 246 { 307 247 ASSERT(numPar >= 0 && numPar < mNPar); … … 310 250 } 311 251 312 //++ 252 /*! 253 Idem precedente fonction mais pour tous les parametres. 254 */ 313 255 void GeneralXi2::SetDeltaParm(double const* dparam) 314 //315 // Idem precedente fonction mais pour tous les parametres.316 //--317 256 { 318 257 for(int i=0;i<mNPar;i++) deltaParm[i] = dparam[i]; 319 258 } 320 321 //////////////////////////////////////////////////////////////////////322 // Rappel des inline functions pour commentaires323 //++324 // virtual double Value(GeneralFitData& data, double const* parm, int& ndataused)=0;325 // Valeur du Xi2 a definir par l'utilisateur (fct virtuelle pure)326 // a partir des donnees de `data'. l'utilisateur doit egalement327 // retourner le nombre de points de mesure utilises dans le calcul328 // du Xi2 (`ndataused').329 //--330 //++331 // inline int NPar() const332 // Retourne le nombre de parametres Ai.333 //--334 259 335 260 //================================================================ … … 338 263 // Christophe 8/11/93 La Silla 339 264 // re-codage C++ 16/01/96 Saclay 340 341 //++ 342 // Class GeneralFit 343 // Lib Outils++ 344 // include generalfit.h 345 // 346 // Classe de fit d'une GeneralFunction sur une GeneralFitData 347 //-- 348 349 ////////////////////////////////////////////////////////////////////// 350 //++ 265 ////////////////////////////////////////////////////////////////////// 266 /*! 267 Creation d'une classe de fit pour la `GeneralFunction f'. 268 */ 351 269 GeneralFit::GeneralFit(GeneralFunction* f) 352 //353 // Creation d'une classe de fit pour la `GeneralFunction f'.354 //--355 270 : mNVar (f->NVar()), 356 271 mNPar (f->NPar()), … … 385 300 } 386 301 387 //++ 302 /*! 303 Creation d'une classe de fit pour le `GeneralXi2 f'. 304 L'emploi de cette methode n'est pas conseillee car elle 305 calcule automatiquement la derivee 2sd du Xi2 par rapport 306 aux parametres, ce qui entraine un manque de robustesse 307 et qui ne garanti pas que la matrice de covariance soit 308 definie positive (il est possible de surecrire 309 la methode virtuelle Derivee2 pour palier ce probleme). 310 */ 388 311 GeneralFit::GeneralFit(GeneralXi2* f) 389 //390 // Creation d'une classe de fit pour le `GeneralXi2 f'.391 // L'emploi de cette methode n'est pas conseillee car elle392 // calcule automatiquement la derivee 2sd du Xi2 par rapport393 // aux parametres, ce qui entraine un manque de robustesse394 // et qui ne garanti pas que la matrice de covariance soit395 // definie positive (il est possible de surecrire396 // la methode virtuelle Derivee2 pour palier ce probleme).397 //--398 312 : mNVar (0), 399 313 mNPar (f->NPar()), … … 485 399 } 486 400 487 //++488 401 GeneralFit::~GeneralFit() 489 //490 //--491 402 { 492 403 delete[] fixParam; … … 497 408 498 409 ////////////////////////////////////////////////////////////////////// 499 //++ 410 /*! 411 Pour ecrire les iterations dans le fichier filename 412 */ 500 413 void GeneralFit::WriteStep(char *filename) 501 //502 // Pour ecrire les iterations dans le fichier filename503 //--504 414 { 505 415 … … 513 423 } 514 424 515 //++ 425 /*! 426 Niveau de debug 427 (voir aussi la variable d'environnement PDEBUG_GENERALFIT). 428 */ 516 429 void GeneralFit::SetDebug(int level) 517 //518 // Niveau de debug519 // (voir aussi la variable d'environnement PDEBUG_GENERALFIT).520 //--521 430 { 522 431 debugLevel = ( level < 0 ) ? 0: level; … … 524 433 } 525 434 526 //++ 435 /*! 436 Nombre maximum d'iterations permis. 437 */ 527 438 void GeneralFit::SetMaxStep(int n) 528 //529 // Nombre maximum d'iterations permis.530 //--531 439 { 532 440 maxStep = ( n <= 1 ) ? 100: n; … … 534 442 } 535 443 536 //++ 444 /*! 445 Facteur de multiplication/division de Lambda selon 446 que le Chi2 a augmente ou diminue. 447 */ 537 448 void GeneralFit::SetLambda_Fac(double fac) 538 //539 // Facteur de multiplication/division de Lambda selon540 // que le Chi2 a augmente ou diminue.541 //--542 449 { 543 450 Lambda_Fac = (fac>1.) ? fac : 10.; 544 451 } 545 452 546 //++ 453 /*! 454 Critere de convergence sur le Chi2. 455 */ 547 456 void GeneralFit::SetStopChi2(double s) 548 //549 // Critere de convergence sur le Chi2.550 //--551 457 { 552 458 stopChi2 = ( s <= 0. ) ? 0.01: s; … … 554 460 } 555 461 556 //++ 462 /*! 463 Precision des calculs (cf \ref GeneralFit_Fit "descriptif general"). 464 */ 557 465 void GeneralFit::SetEps(double ep) 558 //559 // Precision des calculs (cf descriptif general).560 //--561 466 { 562 467 ep = (ep<=0.) ? EPS_FIT_MIN: ep; … … 565 470 } 566 471 567 //++ 472 /*! 473 Precision des calculs pour le parametre n. 474 */ 568 475 void GeneralFit::SetEps(int n,double ep) 569 //570 // Precision des calculs pour le parametre n.571 //--572 476 { 573 477 ASSERT(n>=0 && n<mNPar); … … 576 480 } 577 481 578 //++ 482 /*! 483 Critere de convergence sur le nombre de stop en chi2 484 dans le cas ou le chi2 augmente de moins de stopchi2 485 (cf \ref GeneralFit_Fit "descriptif general"). 486 487 Si nstopmx<=0, alors ce critere de convergence n'est pas applique. 488 489 Si stopchi2<=0, alors la valeur generale mise par SetStopChi2() 490 est utilisee. 491 */ 579 492 void GeneralFit::SetStopMx(int nstopmx,double stopchi2) 580 //581 // Critere de convergence sur le nombre de stop en chi2582 // dans le cas ou le chi2 augmente de moins de stopchi2583 // (cf descriptif general).584 // Si nstopmx<=0, alors ce critere de convergence n'est pas applique.585 // Si stopchi2<=0, alors la valeur generale mise par SetStopChi2()586 // est utilisee.587 //--588 493 { 589 494 nStopMx = (nstopmx>0) ? nstopmx : 0; … … 593 498 } 594 499 595 //++ 500 /*! 501 Critere de convergence sur le nombre de stop en chi2 502 dans le cas ou le chi2 diminue (cf \ref GeneralFit_Fit "descriptif general"). 503 504 Si nstopl<=0, alors ce critere de convergence n'est pas applique. 505 */ 596 506 void GeneralFit::SetStopLent(int nstoplent) 597 //598 // Critere de convergence sur le nombre de stop en chi2599 // dans le cas ou le chi2 diminue (cf descriptif general).600 // Si nstopl<=0, alors ce critere de convergence n'est pas applique.601 //--602 507 { 603 508 nStopLent = (nstoplent>0) ? nstoplent : 0; … … 606 511 607 512 ////////////////////////////////////////////////////////////////////// 608 //++ 513 /*! 514 Pour changer la fonction a fitter en cours de route 515 (On ne peut passer d'un fit sur une GeneralFunction 516 a un fit sur un GeneralXi2 sans recreer la classe). 517 */ 609 518 void GeneralFit::SetFunction(GeneralFunction* f) 610 //611 // Pour changer la fonction a fitter en cours de route612 // (On ne peut passer d'un fit sur une GeneralFunction613 // a un fit sur un GeneralXi2 sans recreer la classe).614 //--615 519 { 616 520 ASSERT( mFuncXi2 == NULL ); … … 622 526 } 623 527 624 //++ 528 /*! 529 Pour changer le Xi2 a fitter en cours de route 530 (On ne peut passer d'un fit sur une GeneralFunction 531 a un fit sur un GeneralXi2 sans recreer la classe). 532 */ 625 533 void GeneralFit::SetFuncXi2(GeneralXi2* f) 626 //627 // Pour changer le Xi2 a fitter en cours de route628 // (On ne peut passer d'un fit sur une GeneralFunction629 // a un fit sur un GeneralXi2 sans recreer la classe).630 //--631 534 { 632 535 ASSERT( mFunction == NULL ); … … 638 541 639 542 ////////////////////////////////////////////////////////////////////// 640 //++ 543 /*! 544 Pour connecter une structure de donnees. 545 */ 641 546 void GeneralFit::SetData(GeneralFitData* data) 642 //643 // Pour connecter une structure de donnees.644 //--645 547 { 646 548 ASSERT( data->NVar()==mNVar ); … … 652 554 653 555 ////////////////////////////////////////////////////////////////////// 654 //++ 556 /*! 557 Definition du parametre "n" a fitter. 558 */ 655 559 void GeneralFit::SetParam(int n,double value,double step 656 560 ,double min,double max) 657 //658 // Definition du parametre "n" a fitter.659 //--660 561 { 661 562 ASSERT(n>=0 && n<mNPar); … … 679 580 } 680 581 681 //++ 582 /*! 583 Definition du parametre "n" a fitter 584 */ 682 585 void GeneralFit::SetParam(int n, string const& name 683 586 ,double value,double step,double min,double max) 684 //685 // Definition du parametre "n" a fitter686 //--687 587 { 688 588 ASSERT(n>=0 && n<mNPar); … … 692 592 } 693 593 694 //++ 594 /*! 595 Definition du parametre "n" a fitter 596 */ 695 597 void GeneralFit::SetParam(int n,double value) 696 //697 // Definition du parametre "n" a fitter698 //--699 598 { 700 599 ASSERT(n>=0 && n<mNPar); … … 704 603 705 604 ////////////////////////////////////////////////////////////////////// 706 //++ 605 /*! 606 Definition du pas de depart du parametre "n" 607 Si negatif ou nul, parametre fixe. 608 */ 707 609 void GeneralFit::SetStep(int n,double step) 708 //709 // Definition du pas de depart du parametre "n"710 // Si negatif ou nul, parametre fixe.711 //--712 610 { 713 611 ASSERT(n>=0 && n<mNPar); … … 721 619 } 722 620 723 //++ 621 /*! 622 Definition du pas minimum `val' pour le parametre `i' 623 pouvant etre utilise dans le calcul automatique des derivees 624 (soit de la fonction, soit du Xi2 selon les parametres du fit). 625 Si nul pas de limite, si negatif alors `EPS(i)' (cf SetEps). 626 Inutile dans le cas ou les derivees sont donnees 627 par l'utilisateur. 628 */ 724 629 void GeneralFit::SetMinStepDeriv(int i,double val) 725 //726 // Definition du pas minimum `val' pour le parametre `i'727 // pouvant etre utilise dans le calcul automatique des derivees728 // (soit de la fonction, soit du Xi2 selon les parametres du fit).729 // Si nul pas de limite, si negatif alors `EPS(i)' (cf SetEps).730 // Inutile dans le cas ou les derivees sont donnees731 // par l'utilisateur.732 //--733 630 { 734 631 ASSERT(i>=0 && i<mNPar); … … 738 635 } 739 636 740 //++ 637 /*! 638 Definition du pas minimum `val' pour tout les parametres 639 (voir description SetMinStepDeriv ci-dessus). 640 */ 741 641 void GeneralFit::SetMinStepDeriv(double val) 742 //743 // Definition du pas minimum `val' pour tout les parametres744 // (voir description SetMinStepDeriv ci-dessus).745 //--746 642 { 747 643 if(debugLevel>0) cout<<"SetMinStepDeriv "<<val<<endl; … … 750 646 751 647 ////////////////////////////////////////////////////////////////////// 752 //++ 648 /*! 649 Definition des bornes du parametre "n" 650 Si max<=min, parametre non-borne. 651 */ 753 652 void GeneralFit::SetBound(int n, double min, double max) 754 //755 // Definition des bornes du parametre "n"756 // Si max<=min, parametre non-borne.757 //--758 653 { 759 654 ASSERT(n>=0 && n<mNPar && max>min); … … 770 665 } 771 666 772 //++ 667 /*! 668 Pour re-borner le parametre "n" aux bornes par defaut 669 */ 773 670 void GeneralFit::SetBound(int n) 774 //775 // Pour re-borner le parametre "n" aux bornes par defaut776 //--777 671 { 778 672 ASSERT(n>=0 && n<mNPar && maxParam(n)>minParam(n)); … … 780 674 } 781 675 782 //++ 676 /*! 677 Pour ne plus borner le parametre "n" 678 */ 783 679 void GeneralFit::SetUnBound(int n) 784 //785 // Pour ne plus borner le parametre "n"786 //--787 680 { 788 681 ASSERT(n>=0 && n<mNPar); … … 796 689 } 797 690 798 //++ 691 /*! 692 Pour ne plus borner tous les parametres 693 */ 799 694 void GeneralFit::SetUnBound() 800 //801 // Pour ne plus borner tous les parametres802 //--803 695 { 804 696 for(int i=0;i<mNPar;i++) SetUnBound(i); … … 806 698 807 699 ////////////////////////////////////////////////////////////////////// 808 //++ 700 /*! 701 Pour fixer le parametre "n" a la valeur "v" 702 */ 809 703 void GeneralFit::SetFix(int n,double v) 810 //811 // Pour fixer le parametre "n" a la valeur "v"812 //--813 704 { 814 705 ASSERT(n>=0 && n<mNPar); … … 825 716 } 826 717 827 //++ 718 /*! 719 Pour fixer le parametre "n" a la valeur par defaut 720 */ 828 721 void GeneralFit::SetFix(int n) 829 //830 // Pour fixer le parametre "n" a la valeur par defaut831 //--832 722 { 833 723 ASSERT(n>=0 && n<mNPar); … … 835 725 } 836 726 837 //++ 727 /*! 728 Pour liberer le parametre "n" 729 */ 838 730 void GeneralFit::SetFree(int n) 839 //840 // Pour liberer le parametre "n"841 //--842 731 { 843 732 ASSERT(n>=0 && n<mNPar); … … 855 744 } 856 745 857 //++ 746 /*! 747 Pour liberer tous les parametres 748 */ 858 749 void GeneralFit::SetFree() 859 //860 // Pour liberer tous les parametres861 //--862 750 { 863 751 for(int i=0;i<mNPar;i++) SetFree(i); … … 865 753 866 754 ////////////////////////////////////////////////////////////////////// 867 //++ 755 /*! 756 Retourne la valeur du parametre "n" 757 */ 868 758 double GeneralFit::GetParm(int n) 869 //870 // Retourne la valeur du parametre "n"871 //--872 759 { 873 760 ASSERT(n>=0 && n<mNPar); … … 875 762 } 876 763 877 //++ 764 /*! 765 Retourne les valeurs des parametres dans un vecteur. 766 */ 878 767 Vector GeneralFit::GetParm() 879 //880 // Retourne les valeurs des parametres dans un vecteur.881 //--882 768 { 883 769 return Param; 884 770 } 885 771 886 //++ 772 /*! 773 Retourne la valeur de l'erreur du parametre "n" 774 */ 887 775 double GeneralFit::GetParmErr(int n) 888 //889 // Retourne la valeur de l'erreur du parametre "n"890 //--891 776 { 892 777 ASSERT(n>=0 && n<mNPar); … … 894 779 } 895 780 896 //++ 781 /*! 782 Retourne la covariance pour les parametre `i' et `j' 783 */ 897 784 double GeneralFit::GetCoVar(int i,int j) 898 //899 // Retourne la covariance pour les parametre `i' et `j'900 //--901 785 { 902 786 ASSERT(i>=0 && i<mNPar && j>=0 && j<mNPar); … … 905 789 906 790 ////////////////////////////////////////////////////////////////////// 907 //++ 791 /*! 792 Retourne la valeur du pas du parametre "n" 793 */ 908 794 double GeneralFit::GetStep(int n) 909 //910 // Retourne la valeur du pas du parametre "n"911 //--912 795 { 913 796 ASSERT(n>=0 && n<mNPar); … … 915 798 } 916 799 917 //++ 800 /*! 801 Retourne la valeur de la borne superieure du parametre "n" 802 */ 918 803 double GeneralFit::GetMax(int n) 919 //920 // Retourne la valeur de la borne superieure du parametre "n"921 //--922 804 { 923 805 ASSERT(n>=0 && n<mNPar); … … 925 807 } 926 808 927 //++ 809 /*! 810 Retourne la valeur de la borne inferieure du parametre "n" 811 */ 928 812 double GeneralFit::GetMin(int n) 929 //930 // Retourne la valeur de la borne inferieure du parametre "n"931 //--932 813 { 933 814 ASSERT(n>=0 && n<mNPar); … … 936 817 937 818 ////////////////////////////////////////////////////////////////////// 938 //++ 819 /*! 820 Impression du status du fit 821 */ 939 822 void GeneralFit::PrintStatus() 940 //941 // Impression du status du fit942 //--943 823 { 944 824 cout<<"GeneralFit::PrintStatus" … … 962 842 } 963 843 964 //++ 844 /*! 845 Impression des resultats du fit 846 */ 965 847 void GeneralFit::PrintFit() 966 //967 // Impression des resultats du fit968 //--969 848 { 970 849 cout<<"PrintFit: Chi2="<<Chi2 … … 978 857 } 979 858 980 //++ 859 /*! 860 Impression des informations relatives au parametre "n" 861 */ 981 862 void GeneralFit::PrintParm(int n) 982 //983 // Impression des informations relatives au parametre "n"984 //--985 863 { 986 864 ASSERT(n>=0 && n<mNPar); … … 999 877 } 1000 878 1001 //++ 879 /*! 880 Impression des informations relatives a tous les parametres 881 */ 1002 882 void GeneralFit::PrintParm() 1003 //1004 // Impression des informations relatives a tous les parametres1005 //--1006 883 { 1007 884 cout<<"*** Parametres : fix bnd : par err : step min max : eps dmin\n"; … … 1011 888 1012 889 ////////////////////////////////////////////////////////////////////// 1013 //++ 890 /*! 891 Methode de fit. 892 \anchor GeneralFit_Fit 893 \verbatim 894 Fonction de fit de la fonction f(x,y,z,...:p1,p2,...,pn) 895 sur les donnees x[i],y[i],z[i],...,F[i],ErrF[i] 896 - Methode: fit des moindres carres dans le cas non lineaire 897 - Reference: Statistical and Computational Methods in Data Analysis 898 Siegmund Brandt, North-Holland 1970 p 204-206. 899 Introduction des limites pour la variation des parametres (cmv). 900 Increment des parametres selon la methode de Levenberg-Marquardt 901 (Numerical Recipes in C, chap 15 Modeling of Data, Nonlinear Models, 902 Levenberg-Marquardt Method p683) 903 - Gestion des parametres bornes: 904 si p est un parametre borne entre pmin et pmax, le parametre fitte est q 905 tel que q = tang((p-C)/D) .... p = C + D*atan(q) 906 ou C = (pmin+pmax)/2. et D = (pmax-pmin)/Pi 907 On a dq = (1+q**2)/D * dp .... dp = D/(1+q**2) * dq 908 et dF/dq = dF/dp * dp/dq = D/(1+q**2) * dF/dp 909 dF/dp = dF/dq * dq/dp = (1+q**2)/D * dF/dp 910 ^ q 911 | | *| "tang()" 912 | | *| 913 | | *| 914 | | * | 915 | | * | 916 | | * | 917 | | * | 918 Pmin| C| * |Pmax 919 --------------|---------------*---------------|--------------> p 920 -Pi/2| * |0 |Pi/2 921 | * | | 922 | * | | 923 | * | | 924 | * | | 925 |* | | 926 |* | | 927 |* | | 928 <------------------- D ---------> 929 930 - Criteres de convergence, arrets standards: 931 - SOIT: le Chi2 est descendu de moins de stopChi2 932 entre l'iteration n et n+1 933 (stopChi2 est change par SetStopChi2) 934 - SOIT: 1. le chi2 est remonte de moins de stopChi2SMx et 935 2. les parametres libres ont varie de moins de Eps(i) 936 pendant les nStopmx dernieres iterations 937 Si nStopmx<=0, alors ce critere n'est pas applique (def=3). 938 (nStopmx,stopChi2SMx sont changes par SetStopMx, Eps par SetEps) 939 940 - Criteres de convergence, arrets par non-convergence: 941 - plus de "maxStep" iterations. 942 943 - Criteres de convergence, arrets speciaux: 944 - Si l'utilisateur a demande explicitement la methode d'arret 945 "SetStopLent()", arret si : 946 1. le Chi2 est descendu et 947 2. les parametres libres ont varies de moins de Eps 948 pendant les nStopLent dernieres iterations. 949 (nStopLent est change par SetStopLent, Eps par SetEps) 950 951 - Remarques diverses: 952 Les points avec erreurs <=0 ne sont pas utilises dans le fit. 953 Les bornes des parametres ne peuvent etre atteintes 954 - entrees: 955 la fonction est definie par une classe GeneralFunction 956 les donnees sont passees par une classe GeneralFitData 957 le nombre de parametres et le nombre de variables doivent etre 958 coherents entre GeneralFunction GeneralFitData GeneralFit 959 - Return: 960 la function elle meme retourne le nombre d'iterations du fit si succes 961 -1 : si le nombre de degre de liberte est <0 962 -10 : si l'inversion de la matrice des erreurs n'a pas ete possible 963 -11 : si un element diagonal de la matrice des covariances est <=0 964 -20 : si le fit n'a pas converge (nstep>nNstepMX) 965 -100-N : si le parametre "N" est initialise hors limites 966 -200-N : si le parametre "N" atteint sa limite inferieure 967 -300-N : si le parametre "N" atteint sa limite superieure 968 \endverbatim 969 */ 1014 970 int GeneralFit::Fit() 1015 //1016 //--1017 //++1018 //| Fonction de fit de la fonction f(x,y,z,...:p1,p2,...,pn)1019 //| sur les donnees x[i],y[i],z[i],...,F[i],ErrF[i]1020 //| - Methode: fit des moindres carres dans le cas non lineaire1021 //| - Reference: Statistical and Computational Methods in Data Analysis1022 //| Siegmund Brandt, North-Holland 1970 p 204-206.1023 //| Introduction des limites pour la variation des parametres (cmv).1024 //| Increment des parametres selon la methode de Levenberg-Marquardt1025 //| (Numerical Recipes in C, chap 15 Modeling of Data, Nonlinear Models,1026 //| Levenberg-Marquardt Method p683)1027 //--1028 //++1029 //| - Gestion des parametres bornes:1030 //| si p est un parametre borne entre pmin et pmax, le parametre fitte est q1031 //| tel que q = tang((p-C)/D) .... p = C + D*atan(q)1032 //| ou C = (pmin+pmax)/2. et D = (pmax-pmin)/Pi1033 //| On a dq = (1+q**2)/D * dp .... dp = D/(1+q**2) * dq1034 //| et dF/dq = dF/dp * dp/dq = D/(1+q**2) * dF/dp1035 //| dF/dp = dF/dq * dq/dp = (1+q**2)/D * dF/dp1036 //| ^ q1037 //| | | *| "tang()"1038 //| | | *|1039 //| | | *|1040 //| | | * |1041 //| | | * |1042 //| | | * |1043 //| | | * |1044 //| Pmin| C| * |Pmax1045 //| --------------|---------------*---------------|--------------> p1046 //| -Pi/2| * |0 |Pi/21047 //| | * | |1048 //| | * | |1049 //| | * | |1050 //| | * | |1051 //| |* | |1052 //| |* | |1053 //| |* | |1054 //| <------------------- D --------->1055 //--1056 //++1057 //| - Criteres de convergence, arrets standards:1058 //| - SOIT: le Chi2 est descendu de moins de stopChi21059 //| entre l'iteration n et n+11060 //| (stopChi2 est change par SetStopChi2)1061 //| - SOIT: 1. le chi2 est remonte de moins de stopChi2SMx et1062 //| 2. les parametres libres ont varie de moins de Eps(i)1063 //| pendant les nStopmx dernieres iterations1064 //| Si nStopmx<=0, alors ce critere n'est pas applique (def=3).1065 //| (nStopmx,stopChi2SMx sont changes par SetStopMx, Eps par SetEps)1066 //|1067 //| - Criteres de convergence, arrets par non-convergence:1068 //| - plus de "maxStep" iterations.1069 //|1070 //| - Criteres de convergence, arrets speciaux:1071 //| - Si l'utilisateur a demande explicitement la methode d'arret1072 //| "SetStopLent()", arret si :1073 //| 1. le Chi2 est descendu et1074 //| 2. les parametres libres ont varies de moins de Eps1075 //| pendant les nStopLent dernieres iterations.1076 //| (nStopLent est change par SetStopLent, Eps par SetEps)1077 //|1078 //--1079 //++1080 //| - Remarques diverses:1081 //| Les points avec erreurs <=0 ne sont pas utilises dans le fit.1082 //| Les bornes des parametres ne peuvent etre atteintes1083 //| - entrees:1084 //| la fonction est definie par une classe GeneralFunction1085 //| les donnees sont passees par une classe GeneralFitData1086 //| le nombre de parametres et le nombre de variables doivent etre1087 //| coherents entre GeneralFunction GeneralFitData GeneralFit1088 //| - Return:1089 //| la function elle meme retourne le nombre d'iterations du fit si succes1090 //| -1 : si le nombre de degre de liberte est <01091 //| -10 : si l'inversion de la matrice des erreurs n'a pas ete possible1092 //| -11 : si un element diagonal de la matrice des covariances est <=01093 //| -20 : si le fit n'a pas converge (nstep>nNstepMX)1094 //| -100-N : si le parametre "N" est initialise hors limites1095 //| -200-N : si le parametre "N" atteint sa limite inferieure1096 //| -300-N : si le parametre "N" atteint sa limite superieure1097 //--1098 971 { 1099 972 volatile double oldChi2; … … 1385 1258 1386 1259 ////////////////////////////////////////////////////////////////////// 1387 //++ 1260 /*! 1261 Recalcul du Chi2 a partir des parametres courants (`par==NULL') 1262 ou a partir du tableau de parametres `par'. 1263 Retourne le chi2 et le nombre de degres de liberte. 1264 Si nddl<0 probleme. 1265 */ 1388 1266 double GeneralFit::ReCalChi2(int& nddl, double *par) 1389 //1390 // Recalcul du Chi2 a partir des parametres courants (`par==NULL')1391 // ou a partir du tableau de parametres `par'.1392 // Retourne le chi2 et le nombre de degres de liberte.1393 // Si nddl<0 probleme.1394 //--1395 1267 { 1396 1268 double c2 = -1.; … … 1430 1302 1431 1303 ////////////////////////////////////////////////////////////////////// 1432 //++ 1304 /*! 1305 Retourne une structure ``GeneralFitData'' contenant 1306 les residus du fit (val-func) pour les points du fit. 1307 Si ``clean'' est ``true'' 1308 seules les donnees valides de ``data'' sont copiees. 1309 Si ``clean'' est ``false'' (defaut) toutes les donnees 1310 sont copiees et la taille totale de ``data'' est allouee 1311 meme si elle est plus grande que la taille des donnees stoquees. 1312 */ 1433 1313 GeneralFitData GeneralFit::DataResidus(bool clean) 1434 //1435 // Retourne une structure ``GeneralFitData'' contenant1436 // les residus du fit (val-func) pour les points du fit.1437 // Si ``clean'' est ``true''1438 // seules les donnees valides de ``data'' sont copiees.1439 // Si ``clean'' est ``false'' (defaut) toutes les donnees1440 // sont copiees et la taille totale de ``data'' est allouee1441 // meme si elle est plus grande que la taille des donnees stoquees.1442 //--1443 1314 { 1444 1315 if(!mData || !mFunction) … … 1451 1322 1452 1323 ////////////////////////////////////////////////////////////////////// 1453 //++ 1324 /*! 1325 Retourne une structure ``GeneralFitData'' contenant 1326 les valeurs de la fonction fittee pour les points du fit. 1327 (voir commentaires pour ``clean'' dans ``DataResidus'') 1328 */ 1454 1329 GeneralFitData GeneralFit::DataFunction(bool clean) 1455 //1456 // Retourne une structure ``GeneralFitData'' contenant1457 // les valeurs de la fonction fittee pour les points du fit.1458 // (voir commentaires pour ``clean'' dans ``DataResidus'')1459 //--1460 1330 { 1461 1331 if(!mData || !mFunction) … … 1468 1338 1469 1339 ////////////////////////////////////////////////////////////////////// 1470 //++ 1340 /*! 1341 Imprime le commentaire lie a l'erreur rc retournee par Fit() 1342 (voir le commentaire de la methode `Fit()') 1343 */ 1471 1344 void GeneralFit::PrintFitErr(int rc) 1472 //1473 // Imprime le commentaire lie a l'erreur rc retournee par Fit()1474 // (voir le commentaire de la methode `Fit()')1475 //--1476 1345 { 1477 1346 int n; … … 1632 1501 1633 1502 ////////////////////////////////////////////////////////////////////// 1503 /*! 1504 \verbatim 1505 C = (min+max)/2 1506 D = (max-min)/Pi 1507 \endverbatim 1508 */ 1634 1509 void GeneralFit::Set_Bound_C_D(int i) 1635 // C = (min+max)/21636 // D = (max-min)/Pi1637 1510 { 1638 1511 // ASSERT(i>=0 && i<mNPar); … … 1656 1529 1657 1530 ////////////////////////////////////////////////////////////////////// 1531 /*! 1532 \verbatim 1533 tr = tan( (p-C)/D ) 1534 \endverbatim 1535 */ 1658 1536 double GeneralFit::p_vers_tr(int i,double p) 1659 // tr = tan( (p-C)/D )1660 1537 { 1661 1538 // ASSERT(i>=0 && i<mNPar); … … 1687 1564 1688 1565 ////////////////////////////////////////////////////////////////////// 1566 /*! 1567 \verbatim 1568 p = C+D*atan(tr) 1569 \endverbatim 1570 */ 1689 1571 double GeneralFit::tr_vers_p(int i,double tr) 1690 // p = C+D*atan(tr)1691 1572 { 1692 1573 // ASSERT(i>=0 && i<mNPar); … … 1718 1599 1719 1600 ////////////////////////////////////////////////////////////////////// 1601 /*! 1602 \verbatim 1603 dtr = (1+tr**2)/D * dp = (1+tan( (p-C)/D )**2)/D * dp = coeff * dp 1604 attention: df/dp = (1+tr**2)/D * dF/dtr = coeff * dF/dtr 1605 \endverbatim 1606 */ 1720 1607 double GeneralFit::c_dp_vers_dtr(int i,double tr) 1721 // dtr = (1+tr**2)/D * dp = (1+tan( (p-C)/D )**2)/D * dp = coeff * dp1722 // attention: df/dp = (1+tr**2)/D * dF/dtr = coeff * dF/dtr1723 1608 { 1724 1609 // ASSERT(i>=0 && i<mNPar); … … 1750 1635 1751 1636 ////////////////////////////////////////////////////////////////////// 1637 /*! 1638 \verbatim 1639 dp = D/(1+tr**2) * dtr = coeff * dtr 1640 attention: df/dtr = D/(1+tr**2) * dF/dp = coeff * dF/dp 1641 \endverbatim 1642 */ 1752 1643 double GeneralFit::c_dtr_vers_dp(int i,double tr) 1753 // dp = D/(1+tr**2) * dtr = coeff * dtr1754 // attention: df/dtr = D/(1+tr**2) * dF/dp = coeff * dF/dp1755 1644 { 1756 1645 // ASSERT(i>=0 && i<mNPar); … … 1776 1665 1777 1666 ////////////////////////////////////////////////////////////////////// 1667 /*! 1668 \verbatim 1669 1-/ Redefinit dp pour qu'il soit superieur a minStepDeriv 1670 2-/ Redefinit dp pour que p+/-dp reste dans les limites (parametre borne) 1671 Si hors limites alors: 1672 p-dp <= min_p : dp = (p-min_p)*dist 1673 p+dp >= max_p : dp = (max_p-p)*dist 1674 \endverbatim 1675 */ 1778 1676 int GeneralFit::put_in_limits_for_deriv(Vector const& p,Vector& dp,double dist) 1779 // 1-/ Redefinit dp pour qu'il soit superieur a minStepDeriv1780 // 2-/ Redefinit dp pour que p+/-dp reste dans les limites (parametre borne)1781 // Si hors limites alors:1782 // p-dp <= min_p : dp = (p-min_p)*dist1783 // p+dp >= max_p : dp = (max_p-p)*dist1784 1677 { 1785 1678 int nchanged = 0; … … 1826 1719 } 1827 1720 1828 1829 //////////////////////////////////////////////////////////////////////1830 // Rappel des inline functions pour commentaires1831 //++1832 // inline double GetChi2()1833 // Retourne le Chi21834 //--1835 //++1836 // inline double GetChi2Red() const1837 // Retourne le Chi2 reduit1838 //--1839 //++1840 // inline int GetNddl() const1841 // Retourne le nombre de degres de liberte1842 //--1843 //++1844 // inline int GetNStep() const1845 // Retourne le nombre d'iterations1846 //--1847 //++1848 // inline int GetNVar() const1849 // Retourne le nombre de variables1850 //--1851 //++1852 // inline int GetNPar() const1853 // Retourne le nombre de parametres1854 //--1855 //++1856 // inline int GetNFree() const1857 // Retourne le nombre de parametres libres1858 //--1859 //++1860 // inline int GetNBound() const1861 // Retourne le nombre de parametres bornes1862 //--1863 //++1864 // inline int GetNStop() const1865 // Retourne le nstop de convergence1866 //--1867 //++1868 // inline int GetNStopLent() const1869 // Retourne le nstop de convergence lente.1870 //--1871 //++1872 // inline double GetEps(int i)1873 // Retourne la precision de convergence pour le parametre i.1874 //--1875 //++1876 // inline GeneralFunction* GetFunction()1877 // Retourne le pointeur sur la GeneralFunction utilisee.1878 //--1879 //++1880 // inline GeneralFitData* GetGData()1881 // Retourne le pointeur sur la GeneralFitData utilisee.1882 //-- -
trunk/SophyaLib/NTools/generalfit.h
r552 r914 13 13 //================================================================ 14 14 15 16 /*! 17 Classe de fonctions parametrees a plusieurs variables: 18 \f$ F[x1,x2,x3,...:a1,a2,a3,...] \f$ 19 */ 15 20 class GeneralFunction { 16 21 public: … … 18 23 virtual ~GeneralFunction(); 19 24 25 //! Valeur de la fonction a definir par l'utilisateur (fct virtuelle pure) 20 26 virtual double Value(double const xp[], double const* parm)=0; 21 27 virtual double Val_Der(double const xp[], double const* parm … … 25 31 void SetDeltaParm(double const* dparam); 26 32 33 //! Retourne le nombre de variables Xi 27 34 inline int NVar() const {return mNVar;} 35 //! Retourne le nombre de parametres Ai 28 36 inline int NPar() const {return mNPar;} 29 37 30 38 protected: 31 const int mNVar; // nombre de variables f(x,y,z,...)32 const int mNPar; // nombre de parametres39 const int mNVar; //!< nombre de variables f(x,y,z,...) 40 const int mNPar; //!< nombre de parametres 33 41 34 42 double *deltaParm; … … 40 48 //================================================================ 41 49 50 /*! 51 Classe de fonctions parametrees a plusieurs variables 52 derivant de ``GeneralFunction''. Permet de definir 53 une fonction a fiter sans passer par une classe derivee 54 en utilisant l'ecriture courante du C. La fonction 55 retournant les derivees par rapport aux parametres du fit 56 peut etre egalement fournie (optionnel). 57 */ 42 58 class GeneralFunc : public GeneralFunction { 43 59 public: … … 62 78 class GeneralFitData; 63 79 80 /*! 81 Classe de Xi2 a plusieurs parametres : 82 \f$ Xi2[a1,a2,a3,...] \f$ 83 */ 64 84 class GeneralXi2 { 65 85 public: … … 67 87 virtual ~GeneralXi2(); 68 88 89 /*! 90 Valeur du Xi2 a definir par l'utilisateur (fct virtuelle pure) 91 a partir des donnees de `data'. l'utilisateur doit egalement 92 retourner le nombre de points de mesure utilises dans le calcul 93 du Xi2 (`ndataused'). 94 */ 69 95 virtual double Value(GeneralFitData& data, double* parm, int& ndataused)=0; 70 96 virtual double Derivee(GeneralFitData& data, int i, double* parm); … … 74 100 void SetDeltaParm(double const* dparam); 75 101 102 //! Retourne le nombre de parametres Ai. 76 103 inline int NPar() const {return mNPar;} 77 104 78 105 protected: 79 const int mNPar; // nombre de parametres106 const int mNPar; //!< nombre de parametres 80 107 81 108 double *deltaParm; … … 86 113 //================================================================ 87 114 115 //! Classe de fit d'une GeneralFunction sur une GeneralFitData 88 116 class GeneralFit { 89 117 public: … … 129 157 double GetMax(int n); 130 158 double GetMin(int n); 159 //! Retourne le Chi2 131 160 inline double GetChi2() const {return Chi2;}; 161 //! Retourne le Chi2 reduit 132 162 inline double GetChi2Red() const { 133 163 if(mNddl<=0) return (double) mNddl; 134 164 return Chi2/(double) mNddl; 135 165 }; 166 //! Retourne la precision de convergence pour le parametre i. 136 167 inline double GetEps(int i) const {return Eps(i);}; 168 //! Retourne le nombre de degres de liberte 137 169 inline int GetNddl() const {return mNddl;}; 170 //! Retourne le nombre d'iterations 138 171 inline int GetNStep() const {return nStep;}; 172 //! Retourne le nombre de variables 139 173 inline int GetNVar() const {return mNVar;}; 174 //! Retourne le nombre de parametres 140 175 inline int GetNPar() const {return mNPar;}; 176 //! Retourne le nombre de parametres libres 141 177 inline int GetNFree() const {return mNParFree;}; 178 //! Retourne le nombre de parametres bornes 142 179 inline int GetNBound() const {return mNParBound;}; 180 //! Retourne le nstop de convergence 143 181 inline int GetNStop() const {return nStop;}; 182 //! Retourne le nstop de convergence lente. 144 183 inline int GetNStopLent() const {return nStopLent;}; 184 //! Retourne le pointeur sur la GeneralFunction utilisee. 145 185 inline GeneralFunction* GetFunction() const {return mFunction;}; 186 //! Retourne le pointeur sur la GeneralFitData utilisee. 146 187 inline GeneralFitData* GetGData() const {return mData;}; 147 188 … … 158 199 159 200 protected: 160 int mNtry; // numero d'appel de la routine de fit.161 int mNVar; // nombre de variables f(x,y,z,...)162 int mNPar; // nombre de parametres163 int mNParFree; // nombre de parametres libres164 int mNParBound; // nombre de parametres bornes201 int mNtry; //!< numero d'appel de la routine de fit. 202 int mNVar; //!< nombre de variables f(x,y,z,...) 203 int mNPar; //!< nombre de parametres 204 int mNParFree; //!< nombre de parametres libres 205 int mNParBound; //!< nombre de parametres bornes 165 206 GeneralFunction* mFunction; 166 207 GeneralXi2* mFuncXi2;
Note:
See TracChangeset
for help on using the changeset viewer.