DavidonErrorUpdator.cxx

Go to the documentation of this file.
00001 // @(#)root/minuit2:$Id: DavidonErrorUpdator.cxx 27589 2009-02-24 11:23:44Z moneta $
00002 // Authors: M. Winkler, F. James, L. Moneta, A. Zsenei   2003-2005  
00003 
00004 /**********************************************************************
00005  *                                                                    *
00006  * Copyright (c) 2005 LCG ROOT Math team,  CERN/PH-SFT                *
00007  *                                                                    *
00008  **********************************************************************/
00009 
00010 #include "Minuit2/DavidonErrorUpdator.h"
00011 #include "Minuit2/MinimumState.h"
00012 #include "Minuit2/LaSum.h"
00013 #include "Minuit2/LaProd.h"
00014 
00015 //#define DEBUG 
00016 
00017 #if defined(DEBUG) || defined(WARNINGMSG)
00018 #include "Minuit2/MnPrint.h" 
00019 #endif
00020 
00021 
00022 
00023 namespace ROOT {
00024 
00025    namespace Minuit2 {
00026 
00027 
00028 double inner_product(const LAVector&, const LAVector&);
00029 double similarity(const LAVector&, const LASymMatrix&);
00030 double sum_of_elements(const LASymMatrix&);
00031 
00032 MinimumError DavidonErrorUpdator::Update(const MinimumState& s0, 
00033                                          const MinimumParameters& p1,
00034                                          const FunctionGradient& g1) const {
00035 
00036    // update of the covarianze matrix (Davidon formula, see Tutorial, par. 4.8 pag 26)
00037    // in case of delgam > gvg (PHI > 1) use rank one formula 
00038    // see  par 4.10 pag 30
00039 
00040    const MnAlgebraicSymMatrix& v0 = s0.Error().InvHessian();
00041    MnAlgebraicVector dx = p1.Vec() - s0.Vec();
00042    MnAlgebraicVector dg = g1.Vec() - s0.Gradient().Vec();
00043   
00044    double delgam = inner_product(dx, dg);
00045    double gvg = similarity(dg, v0);
00046 
00047 
00048 #ifdef DEBUG
00049    std::cout << "dx = " << dx << std::endl; 
00050    std::cout << "dg = " << dg << std::endl; 
00051    std::cout<<"delgam= "<<delgam<<" gvg= "<<gvg<<std::endl;
00052 #endif
00053 
00054    if (delgam == 0 ) { 
00055 #ifdef WARNINGMSG
00056       MN_INFO_MSG("DavidonErrorUpdator: delgam = 0 : cannot update - return same matrix ");
00057 #endif
00058       return s0.Error();
00059    }
00060 #ifdef WARNINGMSG
00061    if (delgam < 0)  MN_INFO_MSG("DavidonErrorUpdator: delgam < 0 : first derivatives increasing along search line");
00062 #endif
00063 
00064    if (gvg <= 0 ) { 
00065       // since v0 is pos def this gvg can be only = 0 if  dg = 0 - should never be here
00066 #ifdef WARNINGMSG
00067       MN_INFO_MSG("DavidonErrorUpdator: gvg <= 0 : cannot update - return same matrix "); 
00068 #endif
00069       return s0.Error();
00070    }
00071 
00072 
00073    MnAlgebraicVector vg = v0*dg;
00074 
00075    MnAlgebraicSymMatrix vUpd = Outer_product(dx)/delgam - Outer_product(vg)/gvg;
00076 
00077    if(delgam > gvg) {
00078       // use rank 1 formula
00079       vUpd += gvg*Outer_product(MnAlgebraicVector(dx/delgam - vg/gvg));
00080    }
00081 
00082    double sum_upd = sum_of_elements(vUpd);
00083    vUpd += v0;
00084   
00085    double dcov = 0.5*(s0.Error().Dcovar() + sum_upd/sum_of_elements(vUpd));
00086   
00087    return MinimumError(vUpd, dcov);
00088 }
00089 
00090 /*
00091 MinimumError DavidonErrorUpdator::Update(const MinimumState& s0, 
00092                                          const MinimumParameters& p1,
00093                                          const FunctionGradient& g1) const {
00094 
00095   const MnAlgebraicSymMatrix& v0 = s0.Error().InvHessian();
00096   MnAlgebraicVector dx = p1.Vec() - s0.Vec();
00097   MnAlgebraicVector dg = g1.Vec() - s0.Gradient().Vec();
00098   
00099   double delgam = inner_product(dx, dg);
00100   double gvg = similarity(dg, v0);
00101 
00102 //   std::cout<<"delgam= "<<delgam<<" gvg= "<<gvg<<std::endl;
00103   MnAlgebraicVector vg = v0*dg;
00104 //   MnAlgebraicSymMatrix vUpd(v0.Nrow());
00105 
00106 //   MnAlgebraicSymMatrix dd = ( 1./delgam )*outer_product(dx);
00107 //   dd *= ( 1./delgam );
00108 //   MnAlgebraicSymMatrix VggV = ( 1./gvg )*outer_product(vg);
00109 //   VggV *= ( 1./gvg );
00110 //   vUpd = dd - VggV;
00111 //   MnAlgebraicSymMatrix vUpd = ( 1./delgam )*outer_product(dx) - ( 1./gvg )*outer_product(vg);
00112   MnAlgebraicSymMatrix vUpd = Outer_product(dx)/delgam - Outer_product(vg)/gvg;
00113   
00114   if(delgam > gvg) {
00115 //     dx *= ( 1./delgam );
00116 //     vg *= ( 1./gvg );
00117 //     MnAlgebraicVector flnu = dx - vg;
00118 //     MnAlgebraicSymMatrix tmp = Outer_product(flnu);
00119 //     tmp *= gvg;
00120 //     vUpd = vUpd + tmp;
00121     vUpd += gvg*outer_product(dx/delgam - vg/gvg);
00122   }
00123 
00124 //   
00125 //     MnAlgebraicSymMatrix dd = Outer_product(dx);
00126 //     dd *= ( 1./delgam );
00127 //     MnAlgebraicSymMatrix VggV = Outer_product(vg);
00128 //     VggV *= ( 1./gvg );
00129 //     vUpd = dd - VggV;
00130 //   
00131 //     
00132 //   double phi = delgam/(delgam - gvg);
00133 
00134 //   MnAlgebraicSymMatrix vUpd(v0.Nrow());
00135 //   if(phi < 0) {
00136 //     // rank-2 Update
00137 //     MnAlgebraicSymMatrix dd = Outer_product(dx);
00138 //     dd *= ( 1./delgam );
00139 //     MnAlgebraicSymMatrix VggV = Outer_product(vg);
00140 //     VggV *= ( 1./gvg );
00141 //     vUpd = dd - VggV;
00142 //   }
00143 //   if(phi > 1) {
00144 //     // rank-1 Update
00145 //     MnAlgebraicVector tmp = dx - vg;
00146 //     vUpd = Outer_product(tmp);
00147 //     vUpd *= ( 1./(delgam - gvg) );
00148 //   }
00149 //     
00150 
00151 //     
00152 //   if(delgam > gvg) {
00153 //     // rank-1 Update
00154 //     MnAlgebraicVector tmp = dx - vg;
00155 //     vUpd = Outer_product(tmp);
00156 //     vUpd *= ( 1./(delgam - gvg) );
00157 //   } else { 
00158 //     // rank-2 Update
00159 //     MnAlgebraicSymMatrix dd = Outer_product(dx);
00160 //     dd *= ( 1./delgam );
00161 //     MnAlgebraicSymMatrix VggV = Outer_productn(vg);
00162 //     VggV *= ( 1./gvg );
00163 //     vUpd = dd - VggV;
00164 //   }
00165 //   
00166 
00167   double sum_upd = sum_of_elements(vUpd);
00168   vUpd += v0;
00169     
00170 //   MnAlgebraicSymMatrix V1 = v0 + vUpd;
00171 
00172   double dcov = 
00173     0.5*(s0.Error().Dcovar() + sum_upd/sum_of_elements(vUpd));
00174   
00175   return MinimumError(vUpd, dcov);
00176 }
00177 */
00178 
00179   }  // namespace Minuit2
00180 
00181 }  // namespace ROOT

Generated on Tue Jul 5 14:36:48 2011 for ROOT_528-00b_version by  doxygen 1.5.1