CMS 3D CMS Logo

HouseholderDecomposition Class Reference

Implementation of the QR decomposition of a matrix using Householder transformation. More...

#include <Calibration/Tools/interface/HouseholderDecomposition.h>

List of all members.

Public Member Functions

 HouseholderDecomposition (int squareMode_=5, int mineta_=1, int maxeta_=85, int minphi_=1, int maxphi_=20)
 Default constructor.
int indexSqr2Reg (const int &sqrIndex, const int &maxCeta, const int &maxCphi)
 Method to translate from square indices to region indices.
vector< float > iterate (const vector< vector< float > > &eventMatrix, const vector< int > &VmaxCeta, const vector< int > &VmaxCphi, const vector< float > &energyVectorOrig)
 Run the Householder Algorithm. Returns the vector of calibration coefficients.
vector< float > iterate (const vector< vector< float > > &eventMatrix, const vector< int > &VmaxCeta, const vector< int > &VmaxCphi, const vector< float > &energyVector, const int &nIter, const bool &normalizeFlag=false)
 Run the Householder Algorithm several times (nIter).
vector< float > recalibrateEvent (const vector< float > &eventSquare, const int &maxCeta, const int &maxCphi, const vector< float > &recalibrateVector)
 Recalibrate before next iteration: give previous solution vector as argument.
vector< float > runRegional (const vector< vector< float > > &eventMatrix, const vector< int > &VmaxCeta, const vector< int > &VmaxCphi, const vector< float > &energyVector, const int &nIter, const int &regLength=5)
 Run Regional HouseholderAlgorithm (fast version), that splits matrix into regional matrices and inverts them separately.
 ~HouseholderDecomposition ()
 Destructor.

Private Member Functions

bool decompose ()
 Make decomposition input: m=number of events, n=number of channels, qr=event matrix output: qr = transformed event matrix, alpha, pivot returns a boolean value, true if decomposition worked, false if it didn't.
void makeRegions (const int &regLength)
 Determines the regions used for splitting of the full matrix and calibrating separately used by the public runRegional method.
void solve (vector< float > &y)
 Apply transformations to rhs output: r = residual vector (energy vector), y = solution.
vector< vector< float > > unzipMatrix (const vector< vector< float > > &eventMatrix, const vector< int > &VmaxCeta, const vector< int > &VmaxCphi)
 Unzips the skimmed matrix into a full matrix.

Private Attributes

vector< float > alpha
int countEvents
vector< float > energyVectorProc
vector< vector< float > > eventMatrixOrig
vector< vector< float > > eventMatrixProc
int maxeta
int maxphi
int mineta
int minphi
int Nchannels
int Neta
int Nevents
int Nphi
int Nxtals
vector< intpivot
vector< intregMaxEta
vector< intregMaxPhi
vector< intregMinEta
vector< intregMinPhi
float sigmaReplacement
int squareMode


Detailed Description

Implementation of the QR decomposition of a matrix using Householder transformation.

13.03.2007: R.Ofierzynski

Date
2007/03/14 13:55:40
Revision
1.3
Author:
Lorenzo Agostino, R.Ofierzynski, CERN

Definition at line 21 of file HouseholderDecomposition.h.


Constructor & Destructor Documentation

HouseholderDecomposition::HouseholderDecomposition ( int  squareMode_ = 5,
int  mineta_ = 1,
int  maxeta_ = 85,
int  minphi_ = 1,
int  maxphi_ = 20 
)

Default constructor.

Definition at line 14 of file HouseholderDecomposition.cc.

References maxeta, maxphi, mineta, minphi, Nchannels, Neta, Nphi, Nxtals, sigmaReplacement, and squareMode.

00015   :squareMode(squareMode_), mineta(mineta_), maxeta(maxeta_), minphi(minphi_), maxphi(maxphi_), countEvents(0)
00016 {
00017   Neta = maxeta - mineta + 1;
00018   if (mineta * maxeta < 0) Neta--; // there's no eta index = 0
00019   Nphi = maxphi - minphi + 1;
00020   if (Nphi <0) Nphi += 360;
00021   
00022   Nchannels = Neta * Nphi; // no. of channels, get it from edges of the region
00023 
00024   Nxtals = squareMode*squareMode; // no. of xtals in one event
00025 
00026   sigmaReplacement = 0.00001; // the sum of columns is replaced by this value in case it is zero (e.g. dead crystal)
00027 
00028 }

HouseholderDecomposition::~HouseholderDecomposition (  ) 

Destructor.

Definition at line 30 of file HouseholderDecomposition.cc.

00031 {
00032 }


Member Function Documentation

bool HouseholderDecomposition::decompose (  )  [private]

Make decomposition input: m=number of events, n=number of channels, qr=event matrix output: qr = transformed event matrix, alpha, pivot returns a boolean value, true if decomposition worked, false if it didn't.

Definition at line 350 of file HouseholderDecomposition.cc.

References alpha, DeDxTools::beta(), eventMatrixProc, i, j, k, Nchannels, Nevents, pivot, sigmaReplacement, funct::sqrt(), sum(), and y.

Referenced by iterate().

00351 {
00352   int i,j,jbar,k;
00353   float beta,sigma,alphak,eventMatrixkk;
00354   vector<float> y(Nchannels);
00355   vector<float> sum(Nchannels);
00356 
00357   //  cout << "Householder::decompose() started" << endl;
00358   
00359   for (j=0;j<Nchannels;j++) 
00360     {
00361       // jth column sum: squared sum for each crystal
00362       sum[j]=0.;
00363       for (i=0;i<Nevents;i++)
00364         sum[j]+=eventMatrixProc[i][j]*eventMatrixProc[i][j];
00365       
00366       // bookkeeping vector
00367       pivot[j] = j;
00368     }
00369   
00370   for (k=0;k<Nchannels;k++) 
00371     {
00372       // kth Householder transformation
00373       sigma = sum[k];
00374       jbar = k;
00375       
00376       // go through all following columns
00377       // find the largest sumSquared in the following columns
00378       for (j=k+1;j<Nchannels;j++) 
00379         {
00380           if (sum[j] > sigma) 
00381             {
00382               sigma = sum[j];
00383               jbar=j;
00384             }
00385         }
00386 
00387       if (jbar != k) 
00388         {
00389           // column interchange:
00390           //     interchange within: bookkeeping vector, squaredSum, eventMatrixProc 
00391 
00392           i = pivot[k];
00393           pivot[k]=pivot[jbar];
00394           pivot[jbar]=i;
00395 
00396           sum[jbar]=sum[k];
00397           sum[k]=sigma;
00398           
00399           for (i=0;i<Nevents;i++) 
00400             {
00401               sigma=eventMatrixProc[i][k];
00402               eventMatrixProc[i][k]=eventMatrixProc[i][jbar];
00403               eventMatrixProc[i][jbar]=sigma;
00404             }
00405         } // end column interchange
00406 
00407       // now store in sigma the squared sum of the readoutEnergies for this column(crystal)
00408       sigma=0.;
00409       for (i=k;i<Nevents;i++)
00410         {
00411           sigma+=eventMatrixProc[i][k]*eventMatrixProc[i][k];
00412         }
00413 
00414       // found a zero-column, bail out
00415       if (sigma == 0.) 
00416         {
00417 //        cout << "Householder::decompose() failed" << endl;
00418 //        return false;
00419           // rof 14.12.2006: workaround to avoid failure of algorithm because of dead crystals:
00420           sigma = sigmaReplacement;
00421           //      cout << "Householder::decompose - found zero column " << jbar << ", replacing sum of column elements by " << sigma << endl;
00422         }
00423 
00424 
00425       // the following paragraph acts only on the diagonal element:
00426       // if element=0, then calculate alpha & beta
00427 
00428       // take the diagonal element
00429       eventMatrixkk = eventMatrixProc[k][k];
00430 
00431       if (eventMatrixkk < 0.) 
00432         alpha[k] = sqrt(sigma);
00433       else
00434         alpha[k] = sqrt(sigma) * (-1.);
00435 
00436       alphak = alpha[k];
00437 
00438       beta = 1 / (sigma - eventMatrixkk * alphak);
00439       // replace it
00440       eventMatrixProc[k][k] = eventMatrixkk - alphak;
00441 
00442       for (j=k+1; j<Nchannels; j++) 
00443         {
00444           y[j] = 0.;
00445 
00446           for (i=k; i<Nevents; i++)
00447             {
00448               y[j] += eventMatrixProc[i][k] * eventMatrixProc[i][j];
00449             }
00450 
00451           y[j] *= beta;
00452         }
00453 
00454       for (j=k+1; j<Nchannels; j++) 
00455         {
00456           for (i=k; i<Nevents; i++) 
00457             {
00458               eventMatrixProc[i][j] -= eventMatrixProc[i][k] * y[j];
00459               sum[j] -= eventMatrixProc[k][j] * eventMatrixProc[k][j];
00460             }
00461         }
00462     } // end of kth householder transformation
00463   
00464   //  cout << "Householder::decompose() finished" << endl;
00465   
00466   return true;
00467 }

int HouseholderDecomposition::indexSqr2Reg ( const int sqrIndex,
const int maxCeta,
const int maxCphi 
)

Method to translate from square indices to region indices.

Definition at line 532 of file HouseholderDecomposition.cc.

References maxeta, maxphi, mineta, minphi, and squareMode.

Referenced by recalibrateEvent(), runRegional(), and unzipMatrix().

00533 {
00534   int regionIndex;
00535 
00536   // get the current eta, phi indices
00537   int curr_eta = maxCeta - squareMode/2 + sqrIndex%squareMode;
00538   if (curr_eta * maxCeta <= 0) {if (maxCeta > 0) curr_eta--; else curr_eta++; }  // JUMP over 0
00539 
00540   int curr_phi = maxCphi - squareMode/2 + sqrIndex/squareMode;
00541   if (curr_phi < 1) curr_phi += 360;
00542   if (curr_phi > 360) curr_phi -= 360;
00543 
00544   bool negPhiDirection = (maxphi < minphi);
00545   int iFullphi;
00546 
00547   regionIndex = -1;
00548 
00549   if (curr_eta >= mineta && curr_eta <= maxeta)
00550     if ( (!negPhiDirection && (curr_phi >= minphi && curr_phi <= maxphi)) ||
00551          (negPhiDirection && !(curr_phi >= minphi && curr_phi <= maxphi))      ) 
00552       {
00553         iFullphi = curr_phi - minphi;
00554         if (iFullphi < 0) iFullphi += 360;
00555         regionIndex = (curr_eta - mineta) * (maxphi - minphi + 1 + 360*negPhiDirection) + iFullphi;
00556       }
00557 
00558   return regionIndex;
00559 }

vector< float > HouseholderDecomposition::iterate ( const vector< vector< float > > &  eventMatrix,
const vector< int > &  VmaxCeta,
const vector< int > &  VmaxCphi,
const vector< float > &  energyVectorOrig 
)

Run the Householder Algorithm. Returns the vector of calibration coefficients.

Definition at line 196 of file HouseholderDecomposition.cc.

References alpha, GenMuonPlsPt100GeV_cfg::cout, decompose(), e, lat::endl(), energyVectorProc, eventMatrixOrig, eventMatrixProc, i, j, Nchannels, Nevents, pivot, solve(), and unzipMatrix().

00197 {
00198   vector<float> solution; 
00199 
00200   Nevents=eventMatrix.size();      // Number of events to calibrate with
00201 
00202   if (Nchannels > Nevents)
00203     {
00204       cout << "Householder::runIter(): more channels to calibrate than events available. " << endl;
00205       cout << "  Nchannels=" << Nchannels << endl;
00206       cout << "  Nevents=" << Nevents << endl;
00207       cout << " ******************    ERROR   *********************" << endl;
00208       return solution; // empty vector
00209     }
00210 
00211   // input: eventMatrixOrig - the unzipped matrix
00212   eventMatrixOrig = unzipMatrix(eventMatrix,VmaxCeta,VmaxCphi);
00213 
00214  if (eventMatrixOrig.size() != energyVectorOrig.size())
00215     {
00216       cout << "Householder::runIter(): matrix dimensions non-conformant. " << endl;
00217       cout << "  energyVectorOrig.size()=" << energyVectorOrig.size() << endl;
00218       cout << "  eventMatrixOrig.size()=" << eventMatrixOrig.size() << endl;
00219       cout << " ******************    ERROR   *********************" << endl;
00220       return solution; // empty vector
00221     }
00222 
00223 
00224   int i,j;
00225   eventMatrixProc = eventMatrixOrig;
00226   energyVectorProc = energyVectorOrig; // copy energyVectorOrig vector
00227   vector<float> e(Nchannels);
00228   alpha.assign(Nchannels,0.);
00229   pivot.assign(Nchannels,0);
00230   
00231 
00232   //--------------------
00233   bool decomposeSuccess = decompose();
00234 
00235   if( !decomposeSuccess ) 
00236     {
00237       cout << "Householder::runIter(): Failed: Singular condition in decomposition."<< endl;
00238       cout << "***************** PROBLEM in DECOMPOSITION *************************"<<endl;
00239       return solution; // empty vector
00240     }
00241 
00242   /* DBL_EPSILON: Difference between 1.0 and the minimum float greater than 1.0 */
00243   float mydbleps = 2.22045e-16;  //DBL_EPSILON;
00244   float etasqr = mydbleps*mydbleps; 
00245   //  cout << "LOOK at DBL_EPSILON :" << mydbleps <<endl;
00246 
00247 
00248   //--------------------
00249   // apply transformations to rhs - find solution vector
00250   solution.assign(Nchannels,0.);
00251   solve(solution);
00252 
00253 
00254   // compute residual vector energyVectorProc
00255   for (i=0;i<Nevents;i++) 
00256     {
00257       energyVectorProc[i] = energyVectorOrig[i];
00258       for (j=0; j<Nchannels; j++)
00259         {
00260           energyVectorProc[i]-=eventMatrixOrig[i][j]*solution[j];
00261         }
00262     }
00263 
00264 
00265   //--------------------
00266   // compute first correction vector e
00267   solve(e);
00268 
00269   float normy0=0.;
00270   float norme1=0.;
00271   float norme0;
00272     
00273 
00274 
00275 
00276   for (i=0;i<Nchannels;i++) 
00277     {
00278       normy0 += solution[i] * solution[i];
00279       norme1 += e[i] * e[i];
00280     }
00281   
00282 //  cout << "Householder::runIter(): applying first correction";
00283 //  cout << " normy0 = " << normy0;
00284 //  cout << " norme1 = " << norme1 << endl;
00285 
00286   // not attempt at obtaining the solution is made unless the norm of the first
00287   // correction  is significantly smaller than the norm of the initial solution
00288   if (norme1>(0.0625*normy0)) 
00289     {
00290       //      cout << "Householder::runIter(): first correction is too large. Failed." << endl;
00291     }
00292 
00293   // improve the solution
00294   for (i=0; i<Nchannels; i++)
00295     {
00296       solution[i]+=e[i];
00297     }
00298 
00299   //  cout << "Householder::runIter(): improving solution...." << endl;
00300 
00301   //--------------------
00302   // only continue iteration if the correction was significant
00303   while (norme1>(etasqr*normy0)) 
00304     {
00305       //      cout << "Householder::runIter(): norme1 = " << norme1 << endl;
00306     
00307       for (i=0; i<Nevents; i++) 
00308         {
00309           energyVectorProc[i] = energyVectorOrig[i];
00310           for (j=0; j<Nchannels; j++)
00311             {
00312               energyVectorProc[i] -= eventMatrixOrig[i][j] * solution[j];
00313             }
00314         }
00315 
00316     // compute next correction vector
00317     solve(e);
00318 
00319     norme0 = norme1;
00320     norme1 = 0.;
00321 
00322     for (i=0;i<Nchannels;i++)
00323       {
00324         norme1+=e[i]*e[i];
00325       }
00326 
00327     // terminate iteration if the norm of the new correction failed to decrease
00328     // significantly compared to the norm of the previous correction
00329     if (norme1>(0.0625*norme0)) break;
00330 
00331     // apply correction vector
00332     for (i=0;i<Nchannels;i++)
00333       {
00334         solution[i]+=e[i];
00335       }
00336   }
00337 
00338   //clean up
00339   eventMatrixOrig.clear();
00340   eventMatrixProc.clear();
00341   energyVectorProc.clear();
00342   alpha.clear();
00343   pivot.clear();
00344 
00345   
00346   return solution;
00347 }

vector< float > HouseholderDecomposition::iterate ( const vector< vector< float > > &  eventMatrix,
const vector< int > &  VmaxCeta,
const vector< int > &  VmaxCphi,
const vector< float > &  energyVector,
const int nIter,
const bool normalizeFlag = false 
)

Run the Householder Algorithm several times (nIter).

Returns the final vector of calibration coefficients. Comment from author: unless you do a new selection in between the iterations you don't need to run more than once; a second iteration on the same events does not improve the result in this case

Definition at line 137 of file HouseholderDecomposition.cc.

References i, iter, j, Nchannels, Nevents, Nxtals, recalibrateEvent(), and scale.

Referenced by ElectronCalibration::endJob(), ElectronCalibrationUniv::endJob(), and runRegional().

00138 {
00139   Nevents = eventMatrix.size(); // Number of events to calibrate with
00140 
00141   vector<float> totalSolution(Nchannels,1.);
00142   vector<float> iterSolution;
00143   vector<vector<float> > myEventMatrix(eventMatrix);
00144   vector<float> myEnergyVector(energyVector);
00145 
00146   int i, j;
00147 
00148   // Iterate the correction
00149   for (int iter=1;iter<=nIter;iter++) 
00150     {
00151 
00152       // if normalization flag is set, normalize energies
00153       float sumOverEnergy;
00154       if (normalizeFlag)
00155         {
00156           float scale = 0.;
00157           
00158           for (i=0; i<Nevents; i++)
00159             {
00160               sumOverEnergy = 0.;
00161               for (j=0; j<Nxtals; j++) {sumOverEnergy += myEventMatrix[i][j];}
00162               sumOverEnergy /= myEnergyVector[i];
00163               scale += sumOverEnergy;
00164             }
00165           scale /= Nevents;
00166           
00167           for (i=0; i<Nevents; i++) {myEnergyVector[i] *= scale;}         
00168         } // end normalize energies
00169 
00170 
00171 
00172       // now the real work starts:
00173       iterSolution = iterate(myEventMatrix,VmaxCeta,VmaxCphi,myEnergyVector);
00174 
00175       if (iterSolution.empty()) return iterSolution;
00176 
00177       // re-calibrate eventMatrix with solution
00178       for (int ievent = 0; ievent<Nevents; ievent++)
00179         {
00180           myEventMatrix[ievent] = recalibrateEvent(myEventMatrix[ievent], VmaxCeta[ievent], VmaxCphi[ievent], iterSolution);
00181         }
00182 
00183       for (int i=0; i<Nchannels; i++) 
00184         {
00185           // save solution into theCalibVector
00186           totalSolution[i] *= iterSolution[i];
00187         }
00188 
00189     } // end iterate correction
00190 
00191   return totalSolution;
00192 }

void HouseholderDecomposition::makeRegions ( const int regLength  )  [private]

Determines the regions used for splitting of the full matrix and calibrating separately used by the public runRegional method.

Definition at line 582 of file HouseholderDecomposition.cc.

References funct::abs(), i, j, mineta, minphi, Neta, Nphi, regMaxEta, regMaxPhi, regMinEta, regMinPhi, and squareMode.

Referenced by runRegional().

00583 {
00584   //  int regFrame = regLength/2;
00585   int regFrame = squareMode/2;
00586   // first eta:
00587   int remEta = Neta % regLength;
00588   if (remEta > regLength/2) remEta -= regLength;
00589   int numSubRegEta = Neta / regLength + (remEta < 0)*1;
00590 
00591   int addtoEta = remEta / numSubRegEta;
00592   int addtomoreEta = remEta % numSubRegEta; // add "addtomore" number of times (addto+1), remaining times add just (addto)
00593 
00594   // then phi:
00595   int remPhi = Nphi % regLength;
00596   if (remPhi > regLength/2) remPhi -= regLength;
00597   int numSubRegPhi = Nphi / regLength + (remPhi < 0)*1;
00598 
00599   int addtoPhi = remPhi / numSubRegPhi;
00600   int addtomorePhi = remPhi % numSubRegPhi; // add "addtomore" number of times (addto+-1), remaining times add just (addto)
00601 
00602   // now put it all together
00603   int addedLengthEta = 0;
00604   int addedLengthPhi = 0;
00605   int startIndexEta = mineta;
00606   int startIndexPhi;
00607   int endIndexEta = 0;
00608   int endIndexPhi;
00609   for (int i=0; i < numSubRegEta; i++)
00610     {
00611       addedLengthEta = regLength + addtoEta + addtomoreEta/abs(addtomoreEta)*(i<abs(addtomoreEta));
00612       endIndexEta = startIndexEta + addedLengthEta - 1;
00613 
00614       startIndexPhi = minphi;
00615       endIndexPhi = 0;
00616       for (int j=0; j < numSubRegPhi; j++)
00617         {
00618           addedLengthPhi = regLength + addtoPhi + addtomorePhi/abs(addtomorePhi)*(j<abs(addtomorePhi));
00619           endIndexPhi = startIndexPhi + addedLengthPhi - 1;
00620 
00621           regMinPhi.push_back(startIndexPhi - regFrame*(j!=0) );
00622           regMaxPhi.push_back(endIndexPhi + regFrame*(j!=(numSubRegPhi-1)) );
00623           regMinEta.push_back(startIndexEta - regFrame*(i!=0) );
00624           regMaxEta.push_back(endIndexEta + regFrame*(i!=(numSubRegEta-1)) );
00625 
00626           startIndexPhi = endIndexPhi + 1;
00627         }
00628       startIndexEta = endIndexEta + 1;
00629     }
00630 
00631 //  // print it all
00632 //  cout << "Householder::makeRegions created the following regions for calibration:" << endl;
00633 //  for (int i=0; i<regMinEta.size(); i++)
00634 //    cout << "Region " << i << ": eta = " << regMinEta[i] << " to " << regMaxEta[i] << ", phi = " << regMinPhi[i] << " to " << regMaxPhi[i] << endl;
00635 
00636 }

vector< float > HouseholderDecomposition::recalibrateEvent ( const vector< float > &  eventSquare,
const int maxCeta,
const int maxCphi,
const vector< float > &  recalibrateVector 
)

Recalibrate before next iteration: give previous solution vector as argument.

Definition at line 517 of file HouseholderDecomposition.cc.

References i, indexSqr2Reg(), and Nxtals.

Referenced by iterate(), and runRegional().

00518 {
00519   vector<float> newEventSquare(eventSquare);
00520   int iFull;
00521 
00522   for (int i=0; i<Nxtals; i++) 
00523     {
00524       iFull = indexSqr2Reg(i, maxCeta, maxCphi);
00525       if (iFull >=0)
00526         newEventSquare[i] *= recalibrateVector[iFull];
00527     }
00528   return newEventSquare;
00529 }

vector< float > HouseholderDecomposition::runRegional ( const vector< vector< float > > &  eventMatrix,
const vector< int > &  VmaxCeta,
const vector< int > &  VmaxCphi,
const vector< float > &  energyVector,
const int nIter,
const int regLength = 5 
)

Run Regional HouseholderAlgorithm (fast version), that splits matrix into regional matrices and inverts them separately.

Returns the final vector of calibration coefficients. input: eventMatrix - the skimmed event matrix, VmaxCeta, VmaxCphi - vectors containing eta and phi indices of the maximum containment crystal for each event, energyVector - the energy vector, nIter - number of iterations to be performed, regLength - default length of the region (in eta- and phi-indices), regLength=5 recommended Comment from author: if you use the same events, 2 iterations are recommended; the second iteration gives corrections of the order of 0.0001

Definition at line 35 of file HouseholderDecomposition.cc.

References i, i1, i2, indexSqr2Reg(), iter, iterate(), j, makeRegions(), maxeta, maxphi, mineta, minphi, Nchannels, Nevents, Nphi, Nxtals, recalibrateEvent(), regMaxEta, regMaxPhi, regMinEta, regMinPhi, edm::AssociationMap< Tag >::size(), and squareMode.

Referenced by ElectronCalibration::endJob(), and ElectronCalibrationUniv::endJob().

00036 {
00037   // make regions
00038   makeRegions(regLength);
00039 
00040   Nevents = eventMatrix.size(); // Number of events to calibrate with
00041 
00042   vector<float> totalSolution(Nchannels,1.);
00043   vector<float> iterSolution(Nchannels,1.);
00044   vector<vector<float> > myEventMatrix(eventMatrix);
00045   vector<float> myEnergyVector(energyVector);
00046 
00047   int i, j;
00048 
00049   // loop over nIter
00050   for (int iter=1;iter<=nIter;iter++) 
00051     {
00052       // loop over regions
00053       for (int ireg=0; ireg<regMinEta.size(); ireg++)
00054         {
00055           vector<float> regIterSolution, regEnergyVector;
00056           vector<int> regVmaxCeta, regVmaxCphi;
00057           vector<vector<float> > regEventMatrix;
00058 
00059           // initialize new instance with regional min,max indices
00060           HouseholderDecomposition regionalHH(squareMode,regMinEta[ireg],regMaxEta[ireg],regMinPhi[ireg],regMaxPhi[ireg]);
00061 
00062           // copy all events in region into new eventmatrix, energyvector, VmaxCeta, VmaxCphi
00063           for (int ia=0; ia<VmaxCeta.size(); ia++)
00064             {
00065               if ((VmaxCeta[ia] >= regMinEta[ireg]) && (VmaxCeta[ia] <= regMaxEta[ireg])
00066                   && (VmaxCphi[ia] >= regMinPhi[ireg]) && (VmaxCphi[ia] <= regMaxPhi[ireg]))
00067                 {
00068                   // save event, calculate new eventmatrix(truncated) and energy
00069                   regVmaxCeta.push_back(VmaxCeta[ia]);
00070                   regVmaxCphi.push_back(VmaxCphi[ia]);
00071 
00072                   vector<float> regEvent = myEventMatrix[ia];
00073                   float regEnergy = energyVector[ia];
00074                   for (int i2=0; i2<Nxtals; i2++)
00075                     {
00076                       int iFullReg = regionalHH.indexSqr2Reg(i2, VmaxCeta[ia], VmaxCphi[ia]);
00077                       if (iFullReg <0) // crystal outside
00078                         {
00079                           regEnergy -= regEvent[i2];
00080                           regEvent[i2] = 0.;
00081                         }
00082                     }
00083                   regEventMatrix.push_back(regEvent);
00084                   regEnergyVector.push_back(regEnergy);
00085                 }
00086             }
00087 
00088           // calibrate
00089           //      cout << "HouseholderDecomposition::runRegional - Starting calibration of region " << ireg << ": eta " 
00090           //           << regMinEta[ireg] << " to " << regMaxEta[ireg] << ", phi " << regMinPhi[ireg] << " to " << regMaxPhi[ireg] << endl;
00091           regIterSolution = regionalHH.iterate(regEventMatrix, regVmaxCeta, regVmaxCphi, regEnergyVector);
00092           //      cout << "HouseholderDecomposition::runRegional - calibration of region finished. " << endl;
00093 
00094           // save solution into global iterSolution
00095           // don't forget to delete the ones that are on the border !
00096           for (int i1=0; i1<regIterSolution.size(); i1++)
00097             {
00098               int regFrame = regLength/2;
00099               int currRegEtaRange = regMaxEta[ireg] - regMinEta[ireg] + 1;
00100               int currRegPhiRange = regMaxPhi[ireg] - regMinPhi[ireg] + 1;
00101               int currRegEta = i1 / currRegPhiRange + regMinEta[ireg];
00102               int currRegPhi = i1 % currRegPhiRange + regMinPhi[ireg];
00103               int newindex = -100;
00104               // if crystal well inside:
00105               if ( (currRegEta >= (regMinEta[ireg]+regFrame*(!(regMinEta[ireg]==mineta))) ) &&
00106                    (currRegEta <= (regMaxEta[ireg]-regFrame*(!(regMaxEta[ireg]==maxeta))) ) &&
00107                    (currRegPhi >= (regMinPhi[ireg]+regFrame*(!(regMinPhi[ireg]==minphi))) ) &&
00108                    (currRegPhi <= (regMaxPhi[ireg]-regFrame*(!(regMaxPhi[ireg]==maxphi))) ) )
00109                 {
00110                   newindex = (currRegEta-mineta)*Nphi + currRegPhi-minphi;
00111                   iterSolution[newindex] = regIterSolution[i1];
00112                 }
00113             }
00114         } // end loop over regions
00115 
00116       if (iterSolution.empty()) return iterSolution;
00117       
00118       // re-calibrate eventMatrix with solution
00119       for (int ievent = 0; ievent<Nevents; ievent++)
00120         {
00121           myEventMatrix[ievent] = recalibrateEvent(myEventMatrix[ievent], VmaxCeta[ievent], VmaxCphi[ievent], iterSolution);
00122         }
00123       
00124       // save solution into theCalibVector
00125       for (int i=0; i<Nchannels; i++) 
00126         {
00127           totalSolution[i] *= iterSolution[i];
00128         }
00129       
00130     } // end loop over nIter
00131 
00132   return totalSolution;
00133 
00134 }

void HouseholderDecomposition::solve ( vector< float > &  y  )  [private]

Apply transformations to rhs output: r = residual vector (energy vector), y = solution.

Definition at line 470 of file HouseholderDecomposition.cc.

References alpha, energyVectorProc, eventMatrixProc, i, j, Nchannels, Nevents, pivot, and z.

Referenced by iterate().

00471 {
00472   vector<float> z(Nchannels,0.);
00473 
00474   float gamma;
00475   int i,j;
00476 
00477   //  cout << "Householder::solve() begin" << endl;
00478 
00479   for (j=0; j<Nchannels; j++) 
00480     {
00481       // apply jth transformation to the right hand side
00482       gamma = 0.;
00483       for (i=j; i<Nevents; i++)
00484         {
00485           gamma += eventMatrixProc[i][j] * energyVectorProc[i];
00486         }
00487       gamma /= (alpha[j] * eventMatrixProc[j][j]);
00488 
00489       for (i=j; i<Nevents; i++)
00490         {
00491           energyVectorProc[i] += gamma * eventMatrixProc[i][j];
00492         }
00493     }
00494 
00495   z[Nchannels-1] = energyVectorProc[Nchannels-1] / alpha[Nchannels-1];
00496 
00497   for (i=Nchannels-2; i>=0; i--) 
00498     {
00499       z[i] = energyVectorProc[i];
00500       for (j=i+1; j<Nchannels; j++)
00501         {
00502           z[i] -= eventMatrixProc[i][j]*z[j];
00503         }
00504       z[i] /= alpha[i];
00505     }
00506   
00507   for (i=0; i<Nchannels; i++)
00508     {
00509       y[pivot[i]] = z[i];
00510     }
00511   
00512   //  cout << "Householder::solve() finished." << endl;
00513   
00514 }

vector< vector< float > > HouseholderDecomposition::unzipMatrix ( const vector< vector< float > > &  eventMatrix,
const vector< int > &  VmaxCeta,
const vector< int > &  VmaxCphi 
) [private]

Unzips the skimmed matrix into a full matrix.

Definition at line 561 of file HouseholderDecomposition.cc.

References i, indexSqr2Reg(), k, Nchannels, Nevents, and Nxtals.

Referenced by iterate().

00562 {
00563   vector< vector<float> > fullMatrix;
00564 
00565   int iFull;
00566 
00567   for (int i=0; i<Nevents; i++)
00568     {
00569       vector<float> foo(Nchannels,0.);
00570       for (int k=0; k<Nxtals; k++)
00571         {
00572           iFull = indexSqr2Reg(k, VmaxCeta[i], VmaxCphi[i]);
00573           if (iFull >=0)
00574             foo[iFull] = eventMatrix[i][k];
00575         }
00576       fullMatrix.push_back(foo);
00577     }
00578 
00579   return fullMatrix;
00580 }


Member Data Documentation

vector<float> HouseholderDecomposition::alpha [private]

Definition at line 79 of file HouseholderDecomposition.h.

Referenced by decompose(), iterate(), and solve().

int HouseholderDecomposition::countEvents [private]

Definition at line 73 of file HouseholderDecomposition.h.

vector<float> HouseholderDecomposition::energyVectorProc [private]

Definition at line 78 of file HouseholderDecomposition.h.

Referenced by iterate(), and solve().

vector< vector<float> > HouseholderDecomposition::eventMatrixOrig [private]

Definition at line 76 of file HouseholderDecomposition.h.

Referenced by iterate().

vector< vector<float> > HouseholderDecomposition::eventMatrixProc [private]

Definition at line 77 of file HouseholderDecomposition.h.

Referenced by decompose(), iterate(), and solve().

int HouseholderDecomposition::maxeta [private]

Definition at line 74 of file HouseholderDecomposition.h.

Referenced by HouseholderDecomposition(), indexSqr2Reg(), and runRegional().

int HouseholderDecomposition::maxphi [private]

Definition at line 74 of file HouseholderDecomposition.h.

Referenced by HouseholderDecomposition(), indexSqr2Reg(), and runRegional().

int HouseholderDecomposition::mineta [private]

Definition at line 74 of file HouseholderDecomposition.h.

Referenced by HouseholderDecomposition(), indexSqr2Reg(), makeRegions(), and runRegional().

int HouseholderDecomposition::minphi [private]

Definition at line 74 of file HouseholderDecomposition.h.

Referenced by HouseholderDecomposition(), indexSqr2Reg(), makeRegions(), and runRegional().

int HouseholderDecomposition::Nchannels [private]

Definition at line 75 of file HouseholderDecomposition.h.

Referenced by decompose(), HouseholderDecomposition(), iterate(), runRegional(), solve(), and unzipMatrix().

int HouseholderDecomposition::Neta [private]

Definition at line 74 of file HouseholderDecomposition.h.

Referenced by HouseholderDecomposition(), and makeRegions().

int HouseholderDecomposition::Nevents [private]

Definition at line 75 of file HouseholderDecomposition.h.

Referenced by decompose(), iterate(), runRegional(), solve(), and unzipMatrix().

int HouseholderDecomposition::Nphi [private]

Definition at line 74 of file HouseholderDecomposition.h.

Referenced by HouseholderDecomposition(), makeRegions(), and runRegional().

int HouseholderDecomposition::Nxtals [private]

Definition at line 75 of file HouseholderDecomposition.h.

Referenced by HouseholderDecomposition(), iterate(), recalibrateEvent(), runRegional(), and unzipMatrix().

vector<int> HouseholderDecomposition::pivot [private]

Definition at line 80 of file HouseholderDecomposition.h.

Referenced by decompose(), iterate(), and solve().

vector<int> HouseholderDecomposition::regMaxEta [private]

Definition at line 82 of file HouseholderDecomposition.h.

Referenced by makeRegions(), and runRegional().

vector<int> HouseholderDecomposition::regMaxPhi [private]

Definition at line 82 of file HouseholderDecomposition.h.

Referenced by makeRegions(), and runRegional().

vector<int> HouseholderDecomposition::regMinEta [private]

Definition at line 82 of file HouseholderDecomposition.h.

Referenced by makeRegions(), and runRegional().

vector<int> HouseholderDecomposition::regMinPhi [private]

Definition at line 82 of file HouseholderDecomposition.h.

Referenced by makeRegions(), and runRegional().

float HouseholderDecomposition::sigmaReplacement [private]

Definition at line 83 of file HouseholderDecomposition.h.

Referenced by decompose(), and HouseholderDecomposition().

int HouseholderDecomposition::squareMode [private]

Definition at line 73 of file HouseholderDecomposition.h.

Referenced by HouseholderDecomposition(), indexSqr2Reg(), makeRegions(), and runRegional().


The documentation for this class was generated from the following files:
Generated on Tue Jun 9 18:24:47 2009 for CMSSW by  doxygen 1.5.4