Changeset 3703


Ignore:
Timestamp:
04/09/04 21:15:28 (21 years ago)
Author:
gaug
Message:
*** empty log message ***
File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/MagicSoft/Mars/mcalib/MCalibrationChargeCalc.cc

    r3702 r3703  
    4545//
    4646//   PostProcess(): - FinalizePedestals()
    47 //                  - FinalizeAvPedestals()
    4847//                  - FinalizeCharges()
    4948//                  - FinalizeFFactorMethod()
     
    6059//   MCalibrationChargePINDiode
    6160//   MCalibrationQECam
    62 //   MExtractedSignalCam
    63 //   MExtractedSignalBlindPixel
    64 //   MExtractedSignalPINDiode
    6561//   MPedestalCam
    6662//   MBadPixelsCam
     
    361357//  - MCalibrationChargePINDiode
    362358//
    363 // Sets the pulser colour in:
     359// It retrieves the following variables from MCalibrationChargeCam:
     360//
     361//  - fNumHiGainSamples
     362//  - fNumLoGainSamples
     363//
     364// It defines the PixId of every pixel in:
     365//
     366// - MCalibrationChargeCam
     367// - MCalibrationQECam
     368//
     369// It sets all pixels in excluded which have the flag fBadBixelsPix::IsBad() set in:
     370//
     371// - MCalibrationChargePix
     372// - MCalibrationQEPix
     373//
     374// Sets the pulser colour and tests if it has not changed w.r.t. fPulserColor in:
    364375//
    365376// - MCalibrationChargeCam
    366377// - MCalibrationChargeBlindPix (if existing)
    367378// - MCalibrationChargePINDiode (if existing)
    368 //
    369 // It retrieves the following variables from MCalibrationChargeCam:
    370 //
    371 //  - fNumHiGainSamples
    372 //  - fNumLoGainSamples
    373 //
    374 // It defines the PixId of every pixel in:
    375 //
    376 // - MCalibrationChargeCam
    377 // - MCalibrationQECam
    378 //
    379 // It sets all pixels in excluded which have the flag fBadBixelsPix::IsBad() set in:
    380 //
    381 // - MCalibrationChargePix
    382 // - MCalibrationQEPix
    383 //
    384 // It initializes the pulser color in MCalibrationChargeCam, MCalibrationChargeBlindPix
    385 // and MCalibrationChargePINDiode and tests, if it has not changed w.r.t. fPulserColor
    386379//
    387380Bool_t MCalibrationChargeCalc::ReInit(MParList *pList )
     
    495488}
    496489
    497 // ----------------------------------------------------------------------------------
    498 // 
    499 // Retrieves pedestal and pedestal RMS from MPedestalPix
    500 // Retrieves total entries from MPedestalCam
    501 // Sets pedestal*fNumHiGainSamples and pedestal*fNumLoGainSamples in MCalibrationChargePix
    502 // Sets pedRMS *fSqrtHiGainSamples and pedRMS *fSqrtLoGainSamples in MCalibrationChargePix
    503 //
    504 void MCalibrationChargeCalc::FinalizePedestals(const MPedestalPix &ped, MCalibrationChargePix &cal)
    505 {
    506  
    507   //
    508   // get the pedestals
    509   //
    510   const Float_t pedes  = ped.GetPedestal();
    511   const Float_t prms   = ped.GetPedestalRms();
    512   const Float_t num    = TMath::Sqrt((Float_t)fPedestals->GetTotalEntries());
    513 
    514   //
    515   // set them in the calibration camera
    516   //
    517   if (cal.IsHiGainSaturation())
    518     {
    519       cal.SetPedestal(pedes* fNumLoGainSamples,
    520                       prms * fSqrtLoGainSamples,
    521                       prms * fNumLoGainSamples / num);
    522       cal.CalcLoGainPedestal((Float_t)fNumLoGainSamples);
    523     }
    524   else
    525     {
    526       cal.SetPedestal(pedes* fNumHiGainSamples,
    527                       prms * fSqrtHiGainSamples,
    528                       prms * fNumHiGainSamples / num);
    529     }
    530  
    531 }
    532 
    533 // ---------------------------------------------------------------------
    534 //
    535 // Finalize charges per pixel:
    536 // - Check chage validity
    537 // - Calculate the reduced sigma
    538 // - Calculate the number of photo-electrons
    539 //
    540 Bool_t MCalibrationChargeCalc::FinalizeCharges(MCalibrationChargePix &cal, MBadPixelsPix &bad)
    541 {
    542 
    543   //
    544   // The check return kTRUE if:
    545   //
    546   // 1) Pixel has a fitted charge greater than fChargeLimit*PedRMS
    547   // 2) Pixel has a fit error greater than fChargeVarLimit
    548   // 3) Pixel has a fitted charge greater its fChargeRelVarLimit times its charge error
    549   // 4) Pixel has a charge sigma bigger than its Pedestal RMS
    550   //
    551   if (cal.GetMean() < fChargeLimit*cal.GetPedRms())
    552     {
    553       *fLog << warn << GetDescriptor() << ": Fitted Charge: " << cal.GetMean() << " is smaller than "
    554             << fChargeLimit << " Pedestal RMS: " <<  cal.GetPedRms() << " in Pixel  " << cal.GetPixId() << endl;
    555       bad.SetUncalibrated( MBadPixelsPix::kChargeIsPedestal);
    556     }
    557  
    558   if (cal.GetMeanErr() < fChargeErrLimit)
    559     {
    560       *fLog << warn << GetDescriptor() << ": Error of Fitted Charge: " << cal.GetMeanErr()
    561             << " is smaller than " << fChargeErrLimit << " in Pixel  " << cal.GetPixId() << endl;
    562       bad.SetUncalibrated( MBadPixelsPix::kChargeErrNotValid );
    563     }
    564      
    565    if (cal.GetMean() < fChargeRelErrLimit*cal.GetMeanErr())
    566     {
    567       *fLog << warn << GetDescriptor() << ": Fitted Charge: " << cal.GetMean() << " is smaller than "
    568             << fChargeRelErrLimit << "* its error: " << cal.GetMeanErr()
    569             << " in Pixel  " << cal.GetPixId() << endl;
    570       bad.SetUncalibrated( MBadPixelsPix::kChargeRelErrNotValid );
    571     }
    572 
    573   if (cal.GetSigma() < cal.GetPedRms())
    574     {
    575       *fLog << warn << GetDescriptor() << ": Sigma of Fitted Charge: " << cal.GetSigma()
    576             << " smaller than Pedestal RMS: " << cal.GetPedRms() << " in Pixel  " << cal.GetPixId() << endl;
    577       bad.SetUncalibrated( MBadPixelsPix::kChargeSigmaNotValid );
    578     }
    579 
    580   if (bad.IsUnsuitable(MBadPixelsPix::kUnsuitableRun))
    581     return kFALSE;
    582 
    583   if (!cal.CalcReducedSigma())
    584     {
    585       *fLog << warn << GetDescriptor()
    586             << ": Could not calculate reduced sigmas of pixel: " << cal.GetPixId() << endl;
    587       bad.SetUncalibrated(MBadPixelsPix::kChargeIsPedestal);
    588       return kFALSE;
    589     }
    590  
    591   if (!cal.CalcFFactorMethod())
    592     {
    593       *fLog << warn << GetDescriptor()
    594             << ": Could not calculate F-Factor of pixel: " << cal.GetPixId() << endl;
    595       bad.SetUncalibrated(MBadPixelsPix::kDeviatingNumPhes);
    596       return kFALSE;
    597     }
    598 
    599   return kTRUE;
    600 }
    601 
    602 // ------------------------------------------------------------------------
    603 //
    604 // Returns kFALSE if pointer to MExtractedSignalPINDiode is NULL
    605 // Returns kFALSE if pointer to MCalibrationChargePINDiode is NULL
    606 //
    607 // The check returns kFALSE if:
    608 //
    609 // 1) PINDiode has a fitted charge smaller than fChargeLimit*PedRMS
    610 // 2) PINDiode has a fit error smaller than fChargeErrLimit
    611 // 3) PINDiode has a fitted charge smaller its fChargeRelErrLimit times its charge error
    612 // 4) PINDiode has a charge sigma smaller than its Pedestal RMS
    613 //
    614 // Calls:
    615 // - MCalibrationChargePINDiode::CalcFluxOutsidePlexiglass()
    616 //
    617 Bool_t MCalibrationChargeCalc::FinalizePINDiode()
    618 {
    619 
    620   if (!fPINDiode)
    621     return kFALSE; 
    622 
    623   if (fPINDiode->GetMean() < fChargeLimit*fPINDiode->GetPedRms())
    624     {
    625       *fLog << warn << GetDescriptor() << ": Fitted Charge is smaller than "
    626             << fChargeLimit << " Pedestal RMS in PINDiode " << endl;
    627       return kFALSE;
    628     }
    629  
    630   if (fPINDiode->GetMeanErr() < fChargeErrLimit)
    631     {
    632       *fLog << warn << GetDescriptor() << ": Error of Fitted Charge is smaller than "
    633             << fChargeErrLimit << " in PINDiode " << endl;
    634       return kFALSE;
    635     }
    636      
    637   if (fPINDiode->GetMean() < fChargeRelErrLimit*fPINDiode->GetMeanErr())
    638     {
    639       *fLog << warn << GetDescriptor() << ": Fitted Charge is smaller than "
    640             << fChargeRelErrLimit << "* its error in PINDiode " << endl;
    641       return kFALSE;
    642     }
    643      
    644   if (fPINDiode->GetSigma() < fPINDiode->GetPedRms())
    645     {
    646       *fLog << warn << GetDescriptor()
    647             << ": Sigma of Fitted Charge smaller than Pedestal RMS in PINDiode " << endl;
    648       return kFALSE;
    649     }
    650 
    651 
    652   if (!fPINDiode->CalcFluxOutsidePlexiglass())
    653     {
    654       *fLog << warn << "Could not calculate the flux of photons from the PIN Diode, "
    655             << "will skip PIN Diode Calibration " << endl;
    656       return kFALSE;
    657     }
    658  
    659   return kTRUE;
    660 }
    661 
    662 // ------------------------------------------------------------------------
    663 //
    664 // Returns kFALSE if pointer to MExtractedSignalBlindPixel is NULL
    665 // Returns kFALSE if pointer to MCalibrationChargeBlindPix is NULL
    666 //
    667 // The check returns kFALSE if:
    668 //
    669 // 1) fLambda and fLambdaCheck are separated relatively to each other by more than fLambdaCheckLimit
    670 // 2) BlindPixel has an fLambdaErr greater than fLambdaErrLimit
    671 //
    672 // Calls:
    673 // - MCalibrationChargeBlindPix::CalcFluxInsidePlexiglass()
    674 //
    675 Bool_t MCalibrationChargeCalc::FinalizeBlindPixel()
    676 {
    677 
    678   if (!fBlindPixel)
    679     return kFALSE; 
    680 
    681   const Float_t lambda      = fBlindPixel->GetLambda();
    682   const Float_t lambdaerr   = fBlindPixel->GetLambdaErr();
    683   const Float_t lambdacheck = fBlindPixel->GetLambdaCheck();
    684 
    685   if (2.*(lambdacheck-lambda)/(lambdacheck+lambda) < fLambdaCheckLimit)
    686     {
    687       *fLog << warn << GetDescriptor() << ": Lambda and Lambda-Check differ by more than "
    688             << fLambdaCheckLimit << " in the Blind Pixel " << endl;
    689       return kFALSE;
    690     }
    691  
    692   if (lambdaerr < fLambdaErrLimit)
    693     {
    694       *fLog << warn << GetDescriptor() << ": Error of Fitted Lambda is greater than "
    695             << fLambdaErrLimit << " in Blind Pixel " << endl;
    696       return kFALSE;
    697     }
    698      
    699   if (!fBlindPixel->CalcFluxInsidePlexiglass())
    700     {
    701       *fLog << warn << "Could not calculate the flux of photons from the Blind Pixel, "
    702             << "will skip Blind Pixel Calibration " << endl;
    703       return kFALSE;
    704     }
    705  
    706   return kTRUE;
    707 }
    708 
    709 // ------------------------------------------------------------------------
    710 //
    711 //
    712 Bool_t MCalibrationChargeCalc::FinalizeFFactorMethod()
    713 {
    714 
    715   const UInt_t npixels  = fGeom->GetNumPixels();
    716   const UInt_t nareas   = fGeom->GetNumAreas();
    717   const UInt_t nsectors = fGeom->GetNumSectors();
    718 
    719   Float_t lowlim      [nareas];
    720   Float_t upplim      [nareas];
    721   Float_t areavars    [nareas];
    722   Float_t areaweights [nareas], sectorweights [nsectors];
    723   Float_t areaphes    [nareas], sectorphes    [nsectors];
    724   Int_t   numareavalid[nareas], numsectorvalid[nsectors];
    725 
    726   memset(lowlim        ,0, nareas   * sizeof(Float_t));
    727   memset(upplim        ,0, nareas   * sizeof(Float_t));
    728   memset(areaphes      ,0, nareas   * sizeof(Float_t));
    729   memset(areavars      ,0, nareas   * sizeof(Float_t));
    730   memset(areaweights   ,0, nareas   * sizeof(Float_t));
    731   memset(numareavalid  ,0, nareas   * sizeof(Int_t  ));
    732   memset(sectorweights ,0, nsectors * sizeof(Float_t));
    733   memset(sectorphes    ,0, nsectors * sizeof(Float_t));
    734   memset(numsectorvalid,0, nsectors * sizeof(Int_t  ));
    735  
    736   //
    737   // First loop: Get mean number of photo-electrons and the RMS
    738   //             The loop is only to recognize later pixels with very deviating numbers
    739   //
    740   for (UInt_t i=0; i<npixels; i++)
    741     {
    742      
    743       MCalibrationChargePix &pix = (MCalibrationChargePix&)(*fCam)  [i];
    744       MBadPixelsPix         &bad = (*fBadPixels)[i];
    745      
    746       if (!pix.IsFFactorMethodValid())
    747         continue;
    748 
    749       if (!bad.IsCalibrationResultOK())
    750         {
    751           pix.SetFFactorMethodValid(kFALSE);
    752           continue;
    753         }
    754      
    755       const Float_t nphe  = pix.GetPheFFactorMethod();
    756       const Float_t nvar  = pix.GetPheFFactorMethodVar();
    757       const Int_t   aidx  = (*fGeom)[i].GetAidx();
    758 
    759       if (nvar > 0.)
    760         {
    761           areaphes    [aidx] += nphe;
    762           areavars    [aidx] += nvar;
    763           numareavalid[aidx] ++;
    764         }
    765     }
    766 
    767   for (UInt_t i=0; i<nareas; i++)
    768     {
    769       if (numareavalid[i] == 0)
    770         {
    771           *fLog << warn << GetDescriptor() << ": No pixels with valid number of photo-electrons found "
    772                 << "in area index: " << i << endl;
    773           continue;
    774         }
    775 
    776       areaphes[i] = areaphes[i] / numareavalid[i];
    777       areavars[i] = areavars[i] / numareavalid[i];
    778       lowlim  [i] = areaphes[i] - fPheErrLimit*TMath::Sqrt(areavars[i]);
    779       upplim  [i] = areaphes[i] + fPheErrLimit*TMath::Sqrt(areavars[i]);
    780     }
    781 
    782   memset(numareavalid,0,nareas*sizeof(Int_t));
    783   memset(areaphes    ,0,nareas*sizeof(Int_t));
    784   memset(areavars    ,0,nareas*sizeof(Int_t));
    785 
    786   //
    787   // Second loop: Get weighted mean number of photo-electrons and its RMS excluding
    788   //              pixels deviating by more than fPheErrLimit sigma.
    789   //              Set the conversion factor FADC counts to photo-electrons
    790   //
    791   for (UInt_t i=0; i<npixels; i++)
    792     {
    793      
    794       MCalibrationChargePix &pix = (MCalibrationChargePix&)(*fCam)[i];
    795 
    796       if (!pix.IsFFactorMethodValid())
    797         continue;
    798 
    799       const Float_t nvar  = pix.GetPheFFactorMethodVar();
    800 
    801       if (nvar <= 0.)
    802         {
    803           pix.SetFFactorMethodValid(kFALSE);
    804           continue;
    805         }
    806      
    807       MBadPixelsPix         &bad = (*fBadPixels)[i];
    808 
    809       const Int_t   aidx   = (*fGeom)[i].GetAidx();
    810       const Int_t   sector = (*fGeom)[i].GetSector();
    811       const Float_t nphe   = pix.GetPheFFactorMethod();
    812 
    813       if ( nphe < lowlim[aidx] || nphe > upplim[aidx] )
    814         {
    815           *fLog << warn << GetDescriptor() << ": Deviating number of photo-electrons: "
    816                 << Form("%4.2f",nphe) << " out of accepted limits: ["
    817                 << Form("%4.2f%s%4.2f",lowlim[aidx],",",upplim[aidx]) << "] in pixel " << i << endl;
    818           bad.SetUncalibrated( MBadPixelsPix::kDeviatingNumPhes );
    819           bad.SetUnsuitable  ( MBadPixelsPix::kUnreliableRun    );
    820           continue;
    821         }
    822      
    823       const Float_t weight = 1./nvar;
    824      
    825       areaweights   [aidx]   += weight;
    826       areaphes      [aidx]   += weight*nphe;
    827       numareavalid  [aidx]   ++;
    828       sectorweights [sector] += weight;
    829       sectorphes    [sector] += weight*nphe;
    830       numsectorvalid[sector] ++;
    831     }
    832 
    833   for (UInt_t aidx=0; aidx<nareas; aidx++)
    834     {
    835 
    836       MCalibrationChargePix &apix = (MCalibrationChargePix&)fCam->GetAverageArea(aidx);
    837 
    838       if (areaweights[aidx] <= 0. || areaphes[aidx] <= 0.)
    839         {
    840           *fLog << warn << " Mean number of phe's from area index " << aidx << " cannot be calculated: "
    841                 << " Sum of weights: "       << areaweights[aidx]
    842                 << " Sum of weighted phes: " << areaphes[aidx]    << endl;
    843           apix.SetFFactorMethodValid(kFALSE);
    844           continue;
    845         }
    846 
    847       *fLog << inf << "Replacing number photo-electrons of average area idx " << aidx << ": "
    848             << Form("%5.3f%s%5.3f",apix.GetPheFFactorMethod()," +- ",apix.GetPheFFactorMethodErr()) << endl;
    849       *fLog << inf << "  by average number of photo-electrons from area idx " << aidx <<  ": "
    850             << Form("%5.3f%s%5.3f",areaphes[aidx] / areaweights[aidx]," +- ",
    851                     TMath::Sqrt(1./areaweights[aidx])) << endl;
    852 
    853       apix.SetPheFFactorMethod   ( areaphes[aidx]/ areaweights[aidx] );
    854       apix.SetPheFFactorMethodVar(    1.         / areaweights[aidx] );     
    855       apix.SetFFactorMethodValid ( kTRUE );
    856 
    857     }
    858 
    859   for (UInt_t sector=0; sector<nsectors; sector++)
    860     {
    861 
    862       MCalibrationChargePix &spix = (MCalibrationChargePix&)fCam->GetAverageSector(sector);
    863 
    864       if (sectorweights[sector] <= 0. || sectorphes[sector] <= 0.)
    865         {
    866           *fLog << warn << " Mean number of phe's from sector " << sector << " cannot be calculated: "
    867                 << " Sum of weights: "       << sectorweights[sector]
    868                 << " Sum of weighted phes: " << sectorphes[sector]    << endl;
    869           spix.SetFFactorMethodValid(kFALSE);
    870           continue;
    871         }
    872 
    873       *fLog << inf << "Replacing number photo-electrons of average sector " << sector << ": "
    874             << Form("%5.3f%s%5.3f",spix.GetPheFFactorMethod()," +- ",spix.GetPheFFactorMethodErr()) << endl;
    875       *fLog << inf << "   by average number photo-electrons from sector " << sector <<  ": "
    876             << Form("%5.3f%s%5.3f",sectorphes[sector]/ sectorweights[sector]," +- ",
    877                     TMath::Sqrt(1./sectorweights[sector])) << endl;
    878 
    879       spix.SetPheFFactorMethod   ( sectorphes[sector]/ sectorweights[sector] );
    880       spix.SetPheFFactorMethodVar(    1.        / sectorweights[sector] );     
    881       spix.SetFFactorMethodValid ( kTRUE );
    882 
    883     }
    884 
    885   return kTRUE;
    886 }
    887 
    888 
    889 // ----------------------------------------------------------------------
    890 //
    891 // Sets all pixels to MBadPixelsPix::kUnsuitableRun, if following flags are set:
    892 // - MBadPixelsPix::kChargeIsPedestal
    893 // - MBadPixelsPix::kChargeErrNotValid
    894 // - MBadPixelsPix::kChargeRelErrNotValid
    895 // - MBadPixelsPix::kChargeSigmaNotValid
    896 // - MBadPixelsPix::kMeanTimeInFirstBin
    897 // - MBadPixelsPix::kMeanTimeInLast2Bins
    898 //
    899 // Sets all pixels to MBadPixelsPix::kUnreliableRun, if following flags are set:
    900 // - MBadPixelsPix::kDeviatingNumPhes
    901 //
    902 void MCalibrationChargeCalc::FinalizeBadPixels()
    903 {
    904  
    905   for (Int_t i=0; i<fBadPixels->GetSize(); i++)
    906     {
    907      
    908       MBadPixelsPix    &bad    = (*fBadPixels)[i];
    909 
    910       if (bad.IsUncalibrated( MBadPixelsPix::kChargeIsPedestal))
    911         bad.SetUnsuitable(   MBadPixelsPix::kUnsuitableRun   );
    912  
    913       if (bad.IsUncalibrated( MBadPixelsPix::kChargeErrNotValid ))
    914         bad.SetUnsuitable(   MBadPixelsPix::kUnsuitableRun    );
    915 
    916       if (bad.IsUncalibrated( MBadPixelsPix::kChargeRelErrNotValid ))
    917         bad.SetUnsuitable(   MBadPixelsPix::kUnsuitableRun    );
    918  
    919       if (bad.IsUncalibrated( MBadPixelsPix::kChargeSigmaNotValid ))
    920         bad.SetUnsuitable(   MBadPixelsPix::kUnsuitableRun    );
    921 
    922       if (bad.IsUncalibrated( MBadPixelsPix::kMeanTimeInFirstBin ))
    923         bad.SetUnsuitable(   MBadPixelsPix::kUnsuitableRun    );
    924 
    925       if (bad.IsUncalibrated( MBadPixelsPix::kMeanTimeInLast2Bins ))
    926         bad.SetUnsuitable(   MBadPixelsPix::kUnsuitableRun    );
    927 
    928       if (bad.IsUncalibrated( MBadPixelsPix::kDeviatingNumPhes ))
    929         bad.SetUnsuitable(   MBadPixelsPix::kUnreliableRun    );
    930     }
    931 }
    932 
    933 // ------------------------------------------------------------------------
    934 //
    935 //
    936 void MCalibrationChargeCalc::FinalizeFFactorQECam()
    937 {
    938 
    939   MCalibrationChargePix &avpix = (MCalibrationChargePix&)fCam->GetAverageArea(0);
    940   MCalibrationQEPix     &qepix = (MCalibrationQEPix&)  fQECam->GetAverageArea(0); 
    941 
    942   const Float_t avphotons   = avpix.GetPheFFactorMethod()       
    943                            / qepix.GetQEFFactor(fPulserColor)
    944                            / fQECam->GetPlexiglassQE();
    945 
    946   const Float_t avphotrelvar = avpix.GetPheFFactorMethodRelVar()
    947                             + qepix.GetQEFFactorRelVar(fPulserColor)
    948                             + fQECam->GetPlexiglassQERelVar();
    949 
    950   const UInt_t npixels  = fGeom->GetNumPixels();
    951 
    952   for (UInt_t i=0; i<npixels; i++)
    953     {
    954      
    955       MCalibrationChargePix &pix = (MCalibrationChargePix&)(*fCam)[i];
    956       MCalibrationQEPix   &qepix = (MCalibrationQEPix&)  (*fQECam)[i];
    957 
    958       if (!pix.IsFFactorMethodValid())
    959         {
    960           qepix.SetFFactorMethodValid(kFALSE,fPulserColor);
    961           continue;
    962         }
    963      
    964       const Float_t photons = avphotons / fGeom->GetPixRatio(i);
    965       const Float_t qe      = pix.GetPheFFactorMethod() / photons ;
    966 
    967       if (!pix.CalcMeanFFactor( photons , avphotrelvar ))
    968         {
    969           pix.SetFFactorMethodValid(kFALSE);
    970           qepix.SetFFactorMethodValid(kFALSE, fPulserColor);
    971           (*fBadPixels)[i].SetUncalibrated( MBadPixelsPix::kDeviatingNumPhes );
    972         }
    973 
    974       const Float_t qerelvar = avphotrelvar +  pix.GetPheFFactorMethodRelVar();
    975 
    976       qepix.SetQEFFactor    ( qe            , fPulserColor );
    977       qepix.SetQEFFactorVar ( qerelvar*qe*qe, fPulserColor );     
    978       qepix.SetFFactorMethodValid(  kTRUE   , fPulserColor );
    979 
    980       if (!qepix.UpdateFFactorMethod())
    981         *fLog << warn << GetDescriptor() << ": Cannot update Quantum efficiencies with the F-Factor Method" << endl;
    982     }
    983 }
    984 
    985 // ------------------------------------------------------------------------
    986 //
    987 //
    988 void MCalibrationChargeCalc::FinalizeBlindPixelQECam()
    989 {
    990 
    991   const UInt_t npixels  = fGeom->GetNumPixels();
    992  
    993   //
    994   //  With the knowledge of the overall photon flux, calculate the
    995   //  quantum efficiencies after the Blind Pixel and PIN Diode method
    996   //
    997   for (UInt_t i=0; i<npixels; i++)
    998     {
    999      
    1000       MCalibrationQEPix   &qepix = (MCalibrationQEPix&)  (*fQECam)[i];
    1001 
    1002       if (!fBlindPixel)
    1003         {
    1004           qepix.SetBlindPixelMethodValid(kFALSE, fPulserColor);
    1005           continue;
    1006         }
    1007      
    1008       if (!fBlindPixel->IsFluxInsidePlexiglassAvailable())
    1009         {
    1010           qepix.SetBlindPixelMethodValid(kFALSE, fPulserColor);
    1011           continue;
    1012         }
    1013      
    1014       MBadPixelsPix       &bad   =                   (*fBadPixels)[i];
    1015 
    1016       if (!bad.IsUnsuitable (MBadPixelsPix::kUnsuitableRun))
    1017         {
    1018           qepix.SetBlindPixelMethodValid(kFALSE, fPulserColor);
    1019           continue;
    1020         }
    1021      
    1022       MCalibrationChargePix &pix = (MCalibrationChargePix&)(*fCam)[i];
    1023       MGeomPix              &geo =                        (*fGeom)[i];
    1024      
    1025       const Float_t conv       = fBlindPixel->GetFluxInsidePlexiglass()
    1026                               * geo.GetA()
    1027                               / fQECam->GetPlexiglassQE()
    1028                               / pix.GetPheFFactorMethod();
    1029 
    1030       const Float_t convrelvar = fBlindPixel->GetFluxInsidePlexiglassRelVar()
    1031                                + fQECam->GetPlexiglassQERelVar()
    1032                                + pix.GetPheFFactorMethodRelVar();
    1033 
    1034       qepix.SetQEBlindPixel    ( conv                    , fPulserColor );
    1035       qepix.SetQEBlindPixelVar ( convrelvar * conv * conv, fPulserColor );     
    1036       qepix.UpdateBlindPixelMethod();
    1037     }
    1038 }
    1039 
    1040 // ------------------------------------------------------------------------
    1041 //
    1042 //
    1043 void MCalibrationChargeCalc::FinalizePINDiodeQECam()
    1044 {
    1045  
    1046   const UInt_t npixels  = fGeom->GetNumPixels();
    1047 
    1048   //
    1049   //  With the knowledge of the overall photon flux, calculate the
    1050   //  quantum efficiencies after the PIN Diode method
    1051   //
    1052   for (UInt_t i=0; i<npixels; i++)
    1053     {
    1054      
    1055       MCalibrationQEPix   &qepix = (MCalibrationQEPix&)  (*fQECam)[i];
    1056 
    1057       if (!fPINDiode)
    1058         {
    1059           qepix.SetPINDiodeMethodValid(kFALSE, fPulserColor);
    1060           continue;
    1061         }
    1062      
    1063       if (!fPINDiode->IsFluxOutsidePlexiglassAvailable())
    1064         {
    1065           qepix.SetPINDiodeMethodValid(kFALSE, fPulserColor);
    1066           continue;
    1067         }
    1068 
    1069       MBadPixelsPix &bad  =  (*fBadPixels)[i];
    1070 
    1071       if (!bad.IsUnsuitable (MBadPixelsPix::kUnsuitableRun))
    1072         {
    1073           qepix.SetPINDiodeMethodValid(kFALSE, fPulserColor);
    1074           continue;
    1075         }
    1076      
    1077       MCalibrationChargePix &pix = (MCalibrationChargePix&)(*fCam)[i];
    1078       MGeomPix              &geo =                        (*fGeom)[i];
    1079      
    1080       const Float_t conv       = fPINDiode->GetFluxOutsidePlexiglass() * geo.GetA() / pix.GetPheFFactorMethod();
    1081       const Float_t convrelvar = fPINDiode->GetFluxOutsidePlexiglassRelVar() + pix.GetPheFFactorMethodRelVar();
    1082 
    1083       qepix.SetQEPINDiode    ( conv                    , fPulserColor );
    1084       qepix.SetQEPINDiodeVar ( convrelvar * conv * conv, fPulserColor );     
    1085       qepix.UpdateBlindPixelMethod();
    1086     }
    1087 }
    1088 
    1089 
    1090490// -----------------------------------------------------------------------
    1091491//
    1092 // - Finalize the pedestals
    1093 // - Do the quality checks
    1094 // - Calculate the reduced sigma
    1095 // - Calculate the F-Factor Method
     492// Return if number of executions is null.
     493//
     494// First loop over pixels, average areas and sectors, call:
     495//  - FinalizePedestals()
     496//  - FinalizeCharges()
     497// for every entry. Count number of valid pixels in loop and return kFALSE
     498// if there are none (the "Michele check").
     499//
     500// Call FinalizeBadPixels()
     501//
     502// Call FinalizeFFactorMethod() (second and third loop over pixels and areas)
     503//
     504// Call FinalizeBlindPixel()
     505// Call FinalizePINDiode()
     506//
     507// Call  FinalizeFFactorQECam() (fourth loop over pixels and areas)
     508// Call  FinalizeBlindPixelQECam() (fifth loop over pixels and areas)
     509// Call  FinalizePINDiodeQECam() (sixth loop over pixels and areas)
     510// 
     511// Call MParContainer::SetReadyToSave() for fCam, fQECam, fBadPixels and
     512//                                          fBlindPixel and fPINDiode if they exist
     513//
     514// Print out some statistics
    1096515//
    1097516Int_t MCalibrationChargeCalc::PostProcess()
     
    1102521
    1103522  //
    1104   // loop over the pedestal events and check if we have calibration
     523  // First loop over pixels, call FinalizePedestals and FinalizeCharges
    1105524  //
    1106525  Int_t   nvalid      = 0;
     
    1201620  fQECam    ->SetReadyToSave();
    1202621  fBadPixels->SetReadyToSave();
     622
     623  if (fBlindPixel)
     624    fBlindPixel->SetReadyToSave();
     625  if (fPINDiode)
     626    fPINDiode->SetReadyToSave();
     627 
     628
    1203629 
    1204630  *fLog << inf << endl;
     
    1257683}
    1258684
     685// ----------------------------------------------------------------------------------
     686// 
     687// Retrieves pedestal and pedestal RMS from MPedestalPix
     688// Retrieves total entries from MPedestalCam
     689// Sets pedestal*fNumHiGainSamples and pedestal*fNumLoGainSamples in MCalibrationChargePix
     690// Sets pedRMS *fSqrtHiGainSamples and pedRMS *fSqrtLoGainSamples in MCalibrationChargePix
     691//
     692// If the flag MCalibrationPix::IsHiGainSaturation() is set, call also:
     693// - MCalibrationChargePix::CalcLoGainPedestal()
     694//
     695void MCalibrationChargeCalc::FinalizePedestals(const MPedestalPix &ped, MCalibrationChargePix &cal)
     696{
     697 
     698  //
     699  // get the pedestals
     700  //
     701  const Float_t pedes  = ped.GetPedestal();
     702  const Float_t prms   = ped.GetPedestalRms();
     703  const Float_t num    = TMath::Sqrt((Float_t)fPedestals->GetTotalEntries());
     704
     705  //
     706  // set them in the calibration camera
     707  //
     708  if (cal.IsHiGainSaturation())
     709    {
     710      cal.SetPedestal(pedes* fNumLoGainSamples,
     711                      prms * fSqrtLoGainSamples,
     712                      prms * fNumLoGainSamples / num);
     713      cal.CalcLoGainPedestal((Float_t)fNumLoGainSamples);
     714    }
     715  else
     716    {
     717      cal.SetPedestal(pedes* fNumHiGainSamples,
     718                      prms * fSqrtHiGainSamples,
     719                      prms * fNumHiGainSamples / num);
     720    }
     721 
     722}
     723
     724// ----------------------------------------------------------------------------------------------------
     725//
     726// Check fit results validity. Bad Pixels flags are set if:
     727//
     728// 1) Pixel has a mean smaller than fChargeLimit*PedRMS    ( Flag: MBadPixelsPix::kChargeIsPedestal)
     729// 2) Pixel has a mean error smaller than fChargeErrLimit  ( Flag: MBadPixelsPix::kChargeErrNotValid)
     730// 3) Pixel has mean smaller than fChargeRelVarLimit times its mean error
     731//                                                         ( Flag: MBadPixelsPix::kChargeRelErrNotValid)
     732// 4) Pixel has a sigma bigger than its Pedestal RMS       ( Flag: MBadPixelsPix::kChargeSigmaNotValid )
     733//
     734// Further returns if flags: MBadPixelsPix::kUnsuitableRun is set
     735//
     736// Calls MCalibrationChargePix::CalcReducedSigma() and sets flag:  MBadPixelsPix::kChargeIsPedestal
     737//       if not succesful.
     738//
     739// Calls MCalibrationChargePix::CalcFFactorMethod() and sets flag: MBadPixelsPix::kDeviatingNumPhes)
     740//       if not succesful.
     741//
     742Bool_t MCalibrationChargeCalc::FinalizeCharges(MCalibrationChargePix &cal, MBadPixelsPix &bad)
     743{
     744
     745  if (cal.GetMean() < fChargeLimit*cal.GetPedRms())
     746    {
     747      *fLog << warn << GetDescriptor() << ": Fitted Charge: " << cal.GetMean() << " is smaller than "
     748            << fChargeLimit << " Pedestal RMS: " <<  cal.GetPedRms() << " in Pixel  " << cal.GetPixId() << endl;
     749      bad.SetUncalibrated( MBadPixelsPix::kChargeIsPedestal);
     750    }
     751 
     752  if (cal.GetMeanErr() < fChargeErrLimit)
     753    {
     754      *fLog << warn << GetDescriptor() << ": Error of Fitted Charge: " << cal.GetMeanErr()
     755            << " is smaller than " << fChargeErrLimit << " in Pixel  " << cal.GetPixId() << endl;
     756      bad.SetUncalibrated( MBadPixelsPix::kChargeErrNotValid );
     757    }
     758     
     759   if (cal.GetMean() < fChargeRelErrLimit*cal.GetMeanErr())
     760    {
     761      *fLog << warn << GetDescriptor() << ": Fitted Charge: " << cal.GetMean() << " is smaller than "
     762            << fChargeRelErrLimit << "* its error: " << cal.GetMeanErr()
     763            << " in Pixel  " << cal.GetPixId() << endl;
     764      bad.SetUncalibrated( MBadPixelsPix::kChargeRelErrNotValid );
     765    }
     766
     767  if (cal.GetSigma() < cal.GetPedRms())
     768    {
     769      *fLog << warn << GetDescriptor() << ": Sigma of Fitted Charge: " << cal.GetSigma()
     770            << " smaller than Pedestal RMS: " << cal.GetPedRms() << " in Pixel  " << cal.GetPixId() << endl;
     771      bad.SetUncalibrated( MBadPixelsPix::kChargeSigmaNotValid );
     772    }
     773
     774  if (bad.IsUnsuitable(MBadPixelsPix::kUnsuitableRun))
     775    return kFALSE;
     776
     777  if (!cal.CalcReducedSigma())
     778    {
     779      *fLog << warn << GetDescriptor()
     780            << ": Could not calculate reduced sigmas of pixel: " << cal.GetPixId() << endl;
     781      bad.SetUncalibrated(MBadPixelsPix::kChargeIsPedestal);
     782      return kFALSE;
     783    }
     784 
     785  if (!cal.CalcFFactorMethod())
     786    {
     787      *fLog << warn << GetDescriptor()
     788            << ": Could not calculate F-Factor of pixel: " << cal.GetPixId() << endl;
     789      bad.SetUncalibrated(MBadPixelsPix::kDeviatingNumPhes);
     790      return kFALSE;
     791    }
     792
     793  return kTRUE;
     794}
     795
     796
     797
     798// -----------------------------------------------------------------------------------
     799//
     800// Sets pixel to MBadPixelsPix::kUnsuitableRun, if one of the following flags is set:
     801// - MBadPixelsPix::kChargeIsPedestal
     802// - MBadPixelsPix::kChargeErrNotValid
     803// - MBadPixelsPix::kChargeRelErrNotValid
     804// - MBadPixelsPix::kChargeSigmaNotValid
     805// - MBadPixelsPix::kMeanTimeInFirstBin
     806// - MBadPixelsPix::kMeanTimeInLast2Bins
     807//
     808// Sets pixel to MBadPixelsPix::kUnreliableRun, if one of the following flags is set:
     809// - MBadPixelsPix::kDeviatingNumPhes
     810//
     811void MCalibrationChargeCalc::FinalizeBadPixels()
     812{
     813 
     814  for (Int_t i=0; i<fBadPixels->GetSize(); i++)
     815    {
     816     
     817      MBadPixelsPix    &bad    = (*fBadPixels)[i];
     818
     819      if (bad.IsUncalibrated( MBadPixelsPix::kChargeIsPedestal))
     820        bad.SetUnsuitable(   MBadPixelsPix::kUnsuitableRun   );
     821 
     822      if (bad.IsUncalibrated( MBadPixelsPix::kChargeErrNotValid ))
     823        bad.SetUnsuitable(   MBadPixelsPix::kUnsuitableRun    );
     824
     825      if (bad.IsUncalibrated( MBadPixelsPix::kChargeRelErrNotValid ))
     826        bad.SetUnsuitable(   MBadPixelsPix::kUnsuitableRun    );
     827 
     828      if (bad.IsUncalibrated( MBadPixelsPix::kChargeSigmaNotValid ))
     829        bad.SetUnsuitable(   MBadPixelsPix::kUnsuitableRun    );
     830
     831      if (bad.IsUncalibrated( MBadPixelsPix::kMeanTimeInFirstBin ))
     832        bad.SetUnsuitable(   MBadPixelsPix::kUnsuitableRun    );
     833
     834      if (bad.IsUncalibrated( MBadPixelsPix::kMeanTimeInLast2Bins ))
     835        bad.SetUnsuitable(   MBadPixelsPix::kUnsuitableRun    );
     836
     837      if (bad.IsUncalibrated( MBadPixelsPix::kDeviatingNumPhes ))
     838        bad.SetUnsuitable(   MBadPixelsPix::kUnreliableRun    );
     839    }
     840}
     841
     842// ------------------------------------------------------------------------
     843//
     844//
     845// First loop: Calculate a mean and mean RMS of photo-electrons per area index
     846//             Include only pixels which are not MBadPixelsPix::kUnsuitableRun or
     847//             MBadPixelsPix::kUnreliableRun (see FinalizeBadPixels()) and set
     848//             MCalibrationChargePix::SetFFactorMethodValid(kFALSE) in that case.
     849//             
     850// Second loop: Get weighted mean number of photo-electrons and its RMS including
     851//              only pixels with flag MCalibrationChargePix::IsFFactorMethodValid()
     852//              and further exclude those deviating by more than fPheErrLimit mean
     853//              sigmas from the mean (obtained in first loop). Set
     854//              MBadPixelsPix::kDeviatingNumPhes if excluded.
     855//
     856//              Set weighted mean and variance of photo-electrons per area index in:
     857//              average area pixels of MCalibrationChargeCam (obtained from:
     858//              MCalibrationChargeCam::GetAverageArea() )
     859//
     860//              Set weighted mean  and variance of photo-electrons per sector in:
     861//              average sector pixels of MCalibrationChargeCam (obtained from:
     862//              MCalibrationChargeCam::GetAverageSector() )
     863//
     864Bool_t MCalibrationChargeCalc::FinalizeFFactorMethod()
     865{
     866
     867  const UInt_t npixels  = fGeom->GetNumPixels();
     868  const UInt_t nareas   = fGeom->GetNumAreas();
     869  const UInt_t nsectors = fGeom->GetNumSectors();
     870
     871  Float_t lowlim      [nareas];
     872  Float_t upplim      [nareas];
     873  Float_t areavars    [nareas];
     874  Float_t areaweights [nareas], sectorweights [nsectors];
     875  Float_t areaphes    [nareas], sectorphes    [nsectors];
     876  Int_t   numareavalid[nareas], numsectorvalid[nsectors];
     877
     878  memset(lowlim        ,0, nareas   * sizeof(Float_t));
     879  memset(upplim        ,0, nareas   * sizeof(Float_t));
     880  memset(areaphes      ,0, nareas   * sizeof(Float_t));
     881  memset(areavars      ,0, nareas   * sizeof(Float_t));
     882  memset(areaweights   ,0, nareas   * sizeof(Float_t));
     883  memset(numareavalid  ,0, nareas   * sizeof(Int_t  ));
     884  memset(sectorweights ,0, nsectors * sizeof(Float_t));
     885  memset(sectorphes    ,0, nsectors * sizeof(Float_t));
     886  memset(numsectorvalid,0, nsectors * sizeof(Int_t  ));
     887 
     888  //
     889  // First loop: Get mean number of photo-electrons and the RMS
     890  //             The loop is only to recognize later pixels with very deviating numbers
     891  //
     892  for (UInt_t i=0; i<npixels; i++)
     893    {
     894     
     895      MCalibrationChargePix &pix = (MCalibrationChargePix&)(*fCam)  [i];
     896      MBadPixelsPix         &bad = (*fBadPixels)[i];
     897     
     898      if (!pix.IsFFactorMethodValid())
     899        continue;
     900
     901      if (bad.IsUnsuitable(MBadPixelsPix::kUnsuitableRun))
     902        {
     903          pix.SetFFactorMethodValid(kFALSE);
     904          continue;
     905        }
     906
     907      if (bad.IsUnsuitable(MBadPixelsPix::kUnreliableRun))
     908        {
     909          pix.SetFFactorMethodValid(kFALSE);
     910          continue;
     911        }
     912     
     913      const Float_t nphe  = pix.GetPheFFactorMethod();
     914      const Float_t nvar  = pix.GetPheFFactorMethodVar();
     915      const Int_t   aidx  = (*fGeom)[i].GetAidx();
     916
     917      if (nvar > 0.)
     918        {
     919          areaphes    [aidx] += nphe;
     920          areavars    [aidx] += nvar;
     921          numareavalid[aidx] ++;
     922        }
     923    }
     924
     925  for (UInt_t i=0; i<nareas; i++)
     926    {
     927      if (numareavalid[i] == 0)
     928        {
     929          *fLog << warn << GetDescriptor() << ": No pixels with valid number of photo-electrons found "
     930                << "in area index: " << i << endl;
     931          continue;
     932        }
     933
     934      areaphes[i] = areaphes[i] / numareavalid[i];
     935      areavars[i] = areavars[i] / numareavalid[i];
     936      lowlim  [i] = areaphes[i] - fPheErrLimit*TMath::Sqrt(areavars[i]);
     937      upplim  [i] = areaphes[i] + fPheErrLimit*TMath::Sqrt(areavars[i]);
     938    }
     939
     940  memset(numareavalid,0,nareas*sizeof(Int_t));
     941  memset(areaphes    ,0,nareas*sizeof(Int_t));
     942  memset(areavars    ,0,nareas*sizeof(Int_t));
     943
     944  //
     945  // Second loop: Get weighted mean number of photo-electrons and its RMS excluding
     946  //              pixels deviating by more than fPheErrLimit sigma.
     947  //              Set the conversion factor FADC counts to photo-electrons
     948  //
     949  for (UInt_t i=0; i<npixels; i++)
     950    {
     951     
     952      MCalibrationChargePix &pix = (MCalibrationChargePix&)(*fCam)[i];
     953
     954      if (!pix.IsFFactorMethodValid())
     955        continue;
     956
     957      const Float_t nvar  = pix.GetPheFFactorMethodVar();
     958
     959      if (nvar <= 0.)
     960        {
     961          pix.SetFFactorMethodValid(kFALSE);
     962          continue;
     963        }
     964     
     965      MBadPixelsPix         &bad = (*fBadPixels)[i];
     966
     967      const Int_t   aidx   = (*fGeom)[i].GetAidx();
     968      const Int_t   sector = (*fGeom)[i].GetSector();
     969      const Float_t nphe   = pix.GetPheFFactorMethod();
     970
     971      if ( nphe < lowlim[aidx] || nphe > upplim[aidx] )
     972        {
     973          *fLog << warn << GetDescriptor() << ": Deviating number of photo-electrons: "
     974                << Form("%4.2f",nphe) << " out of accepted limits: ["
     975                << Form("%4.2f%s%4.2f",lowlim[aidx],",",upplim[aidx]) << "] in pixel " << i << endl;
     976          bad.SetUncalibrated( MBadPixelsPix::kDeviatingNumPhes );
     977          bad.SetUnsuitable  ( MBadPixelsPix::kUnreliableRun    );
     978          continue;
     979        }
     980     
     981      const Float_t weight = 1./nvar;
     982     
     983      areaweights   [aidx]   += weight;
     984      areaphes      [aidx]   += weight*nphe;
     985      numareavalid  [aidx]   ++;
     986      sectorweights [sector] += weight;
     987      sectorphes    [sector] += weight*nphe;
     988      numsectorvalid[sector] ++;
     989    }
     990
     991  for (UInt_t aidx=0; aidx<nareas; aidx++)
     992    {
     993
     994      MCalibrationChargePix &apix = (MCalibrationChargePix&)fCam->GetAverageArea(aidx);
     995
     996      if (areaweights[aidx] <= 0. || areaphes[aidx] <= 0.)
     997        {
     998          *fLog << warn << " Mean number of phe's from area index " << aidx << " cannot be calculated: "
     999                << " Sum of weights: "       << areaweights[aidx]
     1000                << " Sum of weighted phes: " << areaphes[aidx]    << endl;
     1001          apix.SetFFactorMethodValid(kFALSE);
     1002          continue;
     1003        }
     1004
     1005      *fLog << inf << "Replacing number photo-electrons of average area idx " << aidx << ": "
     1006            << Form("%5.3f%s%5.3f",apix.GetPheFFactorMethod()," +- ",apix.GetPheFFactorMethodErr()) << endl;
     1007      *fLog << inf << "  by average number of photo-electrons from area idx " << aidx <<  ": "
     1008            << Form("%5.3f%s%5.3f",areaphes[aidx] / areaweights[aidx]," +- ",
     1009                    TMath::Sqrt(1./areaweights[aidx])) << endl;
     1010
     1011      apix.SetPheFFactorMethod   ( areaphes[aidx]/ areaweights[aidx] );
     1012      apix.SetPheFFactorMethodVar(    1.         / areaweights[aidx] );     
     1013      apix.SetFFactorMethodValid ( kTRUE );
     1014
     1015    }
     1016
     1017  for (UInt_t sector=0; sector<nsectors; sector++)
     1018    {
     1019
     1020      MCalibrationChargePix &spix = (MCalibrationChargePix&)fCam->GetAverageSector(sector);
     1021
     1022      if (sectorweights[sector] <= 0. || sectorphes[sector] <= 0.)
     1023        {
     1024          *fLog << warn << " Mean number of phe's from sector " << sector << " cannot be calculated: "
     1025                << " Sum of weights: "       << sectorweights[sector]
     1026                << " Sum of weighted phes: " << sectorphes[sector]    << endl;
     1027          spix.SetFFactorMethodValid(kFALSE);
     1028          continue;
     1029        }
     1030
     1031      *fLog << inf << "Replacing number photo-electrons of average sector " << sector << ": "
     1032            << Form("%5.3f%s%5.3f",spix.GetPheFFactorMethod()," +- ",spix.GetPheFFactorMethodErr()) << endl;
     1033      *fLog << inf << "   by average number photo-electrons from sector " << sector <<  ": "
     1034            << Form("%5.3f%s%5.3f",sectorphes[sector]/ sectorweights[sector]," +- ",
     1035                    TMath::Sqrt(1./sectorweights[sector])) << endl;
     1036
     1037      spix.SetPheFFactorMethod   ( sectorphes[sector]/ sectorweights[sector] );
     1038      spix.SetPheFFactorMethodVar(    1.        / sectorweights[sector] );     
     1039      spix.SetFFactorMethodValid ( kTRUE );
     1040
     1041    }
     1042
     1043  return kTRUE;
     1044}
     1045
     1046
     1047// ------------------------------------------------------------------------
     1048//
     1049// Returns kFALSE if pointer to MCalibrationChargeBlindPix is NULL
     1050//
     1051// The check returns kFALSE if:
     1052//
     1053// 1) fLambda and fLambdaCheck are separated relatively to each other by more than fLambdaCheckLimit
     1054// 2) BlindPixel has an fLambdaErr greater than fLambdaErrLimit
     1055//
     1056// Calls:
     1057// - MCalibrationChargeBlindPix::CalcFluxInsidePlexiglass()
     1058//
     1059Bool_t MCalibrationChargeCalc::FinalizeBlindPixel()
     1060{
     1061
     1062  if (!fBlindPixel)
     1063    return kFALSE; 
     1064
     1065  const Float_t lambda      = fBlindPixel->GetLambda();
     1066  const Float_t lambdaerr   = fBlindPixel->GetLambdaErr();
     1067  const Float_t lambdacheck = fBlindPixel->GetLambdaCheck();
     1068
     1069  if (2.*(lambdacheck-lambda)/(lambdacheck+lambda) < fLambdaCheckLimit)
     1070    {
     1071      *fLog << warn << GetDescriptor() << ": Lambda and Lambda-Check differ by more than "
     1072            << fLambdaCheckLimit << " in the Blind Pixel " << endl;
     1073      return kFALSE;
     1074    }
     1075 
     1076  if (lambdaerr < fLambdaErrLimit)
     1077    {
     1078      *fLog << warn << GetDescriptor() << ": Error of Fitted Lambda is greater than "
     1079            << fLambdaErrLimit << " in Blind Pixel " << endl;
     1080      return kFALSE;
     1081    }
     1082     
     1083  if (!fBlindPixel->CalcFluxInsidePlexiglass())
     1084    {
     1085      *fLog << warn << "Could not calculate the flux of photons from the Blind Pixel, "
     1086            << "will skip Blind Pixel Calibration " << endl;
     1087      return kFALSE;
     1088    }
     1089 
     1090  return kTRUE;
     1091}
     1092
     1093// ------------------------------------------------------------------------
     1094//
     1095// Returns kFALSE if pointer to MCalibrationChargePINDiode is NULL
     1096//
     1097// The check returns kFALSE if:
     1098//
     1099// 1) PINDiode has a fitted charge smaller than fChargeLimit*PedRMS
     1100// 2) PINDiode has a fit error smaller than fChargeErrLimit
     1101// 3) PINDiode has a fitted charge smaller its fChargeRelErrLimit times its charge error
     1102// 4) PINDiode has a charge sigma smaller than its Pedestal RMS
     1103//
     1104// Calls:
     1105// - MCalibrationChargePINDiode::CalcFluxOutsidePlexiglass()
     1106//
     1107Bool_t MCalibrationChargeCalc::FinalizePINDiode()
     1108{
     1109
     1110  if (!fPINDiode)
     1111    return kFALSE; 
     1112
     1113  if (fPINDiode->GetMean() < fChargeLimit*fPINDiode->GetPedRms())
     1114    {
     1115      *fLog << warn << GetDescriptor() << ": Fitted Charge is smaller than "
     1116            << fChargeLimit << " Pedestal RMS in PINDiode " << endl;
     1117      return kFALSE;
     1118    }
     1119 
     1120  if (fPINDiode->GetMeanErr() < fChargeErrLimit)
     1121    {
     1122      *fLog << warn << GetDescriptor() << ": Error of Fitted Charge is smaller than "
     1123            << fChargeErrLimit << " in PINDiode " << endl;
     1124      return kFALSE;
     1125    }
     1126     
     1127  if (fPINDiode->GetMean() < fChargeRelErrLimit*fPINDiode->GetMeanErr())
     1128    {
     1129      *fLog << warn << GetDescriptor() << ": Fitted Charge is smaller than "
     1130            << fChargeRelErrLimit << "* its error in PINDiode " << endl;
     1131      return kFALSE;
     1132    }
     1133     
     1134  if (fPINDiode->GetSigma() < fPINDiode->GetPedRms())
     1135    {
     1136      *fLog << warn << GetDescriptor()
     1137            << ": Sigma of Fitted Charge smaller than Pedestal RMS in PINDiode " << endl;
     1138      return kFALSE;
     1139    }
     1140
     1141
     1142  if (!fPINDiode->CalcFluxOutsidePlexiglass())
     1143    {
     1144      *fLog << warn << "Could not calculate the flux of photons from the PIN Diode, "
     1145            << "will skip PIN Diode Calibration " << endl;
     1146      return kFALSE;
     1147    }
     1148 
     1149  return kTRUE;
     1150}
     1151
     1152// ------------------------------------------------------------------------
     1153//
     1154// Calculate the average number of photons outside the plexiglass with the
     1155// formula:
     1156//
     1157// av.Num.photons(area index) = av.Num.Phes(area index)
     1158//                            / MCalibrationQEPix::GetDefaultQE(fPulserColor)
     1159//                            / MCalibrationQECam::GetPlexiglassQE()
     1160//
     1161// Calculate the variance on the average number of photons.
     1162//
     1163// Loop over pixels:
     1164//
     1165// - Continue, if not MCalibrationChargePix::IsFFactorMethodValid() and set:
     1166//                    MCalibrationQEPix::SetFFactorMethodValid(kFALSE,fPulserColor)
     1167//
     1168// - Call MCalibrationChargePix::CalcMeanFFactor(av.Num.photons) and set:
     1169//        MCalibrationQEPix::SetFFactorMethodValid(kFALSE,fPulserColor) if not succesful
     1170//
     1171// - Calculate the quantum efficiency with the formula:
     1172//
     1173//   QE = ( Num.Phes / av.Num.photons ) * MGeomCam::GetPixRatio()
     1174//
     1175// - Set QE in MCalibrationQEPix::SetQEFFactor ( QE, fPulserColor );
     1176// - Set Variance of QE in  MCalibrationQEPix::SetQEFFactorVar ( Variance, fPulserColor );
     1177// - Set bit MCalibrationQEPix::SetFFactorMethodValid(kTRUE,fPulserColor)
     1178//
     1179// - Call MCalibrationQEPix::UpdateFFactorMethod()
     1180//
     1181void MCalibrationChargeCalc::FinalizeFFactorQECam()
     1182{
     1183
     1184  MCalibrationChargePix &avpix = (MCalibrationChargePix&)fCam->GetAverageArea(0);
     1185  MCalibrationQEPix     &qepix = (MCalibrationQEPix&)  fQECam->GetAverageArea(0); 
     1186
     1187  const Float_t avphotons   = avpix.GetPheFFactorMethod()       
     1188                           / qepix.GetQEFFactor(fPulserColor)
     1189                           / fQECam->GetPlexiglassQE();
     1190
     1191  const Float_t avphotrelvar = avpix.GetPheFFactorMethodRelVar()
     1192                            + qepix.GetQEFFactorRelVar(fPulserColor)
     1193                            + fQECam->GetPlexiglassQERelVar();
     1194
     1195  const UInt_t npixels  = fGeom->GetNumPixels();
     1196
     1197  for (UInt_t i=0; i<npixels; i++)
     1198    {
     1199     
     1200      MCalibrationChargePix &pix = (MCalibrationChargePix&)(*fCam)[i];
     1201      MCalibrationQEPix   &qepix = (MCalibrationQEPix&)  (*fQECam)[i];
     1202
     1203      if (!pix.IsFFactorMethodValid())
     1204        {
     1205          qepix.SetFFactorMethodValid(kFALSE,fPulserColor);
     1206          continue;
     1207        }
     1208     
     1209      const Float_t photons = avphotons / fGeom->GetPixRatio(i);
     1210      const Float_t qe      = pix.GetPheFFactorMethod() / photons ;
     1211
     1212      if (!pix.CalcMeanFFactor( photons , avphotrelvar ))
     1213        {
     1214          pix.SetFFactorMethodValid(kFALSE);
     1215          qepix.SetFFactorMethodValid(kFALSE, fPulserColor);
     1216          (*fBadPixels)[i].SetUncalibrated( MBadPixelsPix::kDeviatingNumPhes );
     1217        }
     1218
     1219      const Float_t qerelvar = avphotrelvar +  pix.GetPheFFactorMethodRelVar();
     1220
     1221      qepix.SetQEFFactor    ( qe            , fPulserColor );
     1222      qepix.SetQEFFactorVar ( qerelvar*qe*qe, fPulserColor );     
     1223      qepix.SetFFactorMethodValid(  kTRUE   , fPulserColor );
     1224
     1225      if (!qepix.UpdateFFactorMethod())
     1226        *fLog << warn << GetDescriptor()
     1227              << ": Cannot update Quantum efficiencies with the F-Factor Method" << endl;
     1228    }
     1229}
     1230
     1231
     1232// ------------------------------------------------------------------------
     1233//
     1234// Loop over pixels:
     1235//
     1236// - Continue, if not MCalibrationChargeBlindPix::IsFluxInsidePlexiglassAvailable() and set:
     1237//                    MCalibrationQEPix::SetBlindPixelMethodValid(kFALSE,fPulserColor)
     1238//
     1239// - Calculate the quantum efficiency with the formula:
     1240//
     1241//   QE =  Num.Phes / MCalibrationChargeBlindPix::GetFluxInsidePlexiglass()
     1242//        / MGeomPix::GetA() * MCalibrationQECam::GetPlexiglassQE()
     1243//
     1244// - Set QE in MCalibrationQEPix::SetQEBlindPixel ( QE, fPulserColor );
     1245// - Set Variance of QE in  MCalibrationQEPix::SetQEBlindPixelVar ( Variance, fPulserColor );
     1246// - Set bit MCalibrationQEPix::SetBlindPixelMethodValid(kTRUE,fPulserColor)
     1247//
     1248// - Call MCalibrationQEPix::UpdateBlindPixelMethod()
     1249//
     1250void MCalibrationChargeCalc::FinalizeBlindPixelQECam()
     1251{
     1252
     1253  const UInt_t npixels  = fGeom->GetNumPixels();
     1254 
     1255  //
     1256  //  With the knowledge of the overall photon flux, calculate the
     1257  //  quantum efficiencies after the Blind Pixel and PIN Diode method
     1258  //
     1259  for (UInt_t i=0; i<npixels; i++)
     1260    {
     1261     
     1262      MCalibrationQEPix   &qepix = (MCalibrationQEPix&)  (*fQECam)[i];
     1263
     1264      if (!fBlindPixel)
     1265        {
     1266          qepix.SetBlindPixelMethodValid(kFALSE, fPulserColor);
     1267          continue;
     1268        }
     1269     
     1270      if (!fBlindPixel->IsFluxInsidePlexiglassAvailable())
     1271        {
     1272          qepix.SetBlindPixelMethodValid(kFALSE, fPulserColor);
     1273          continue;
     1274        }
     1275     
     1276      MBadPixelsPix       &bad   =                   (*fBadPixels)[i];
     1277
     1278      if (!bad.IsUnsuitable (MBadPixelsPix::kUnsuitableRun))
     1279        {
     1280          qepix.SetBlindPixelMethodValid(kFALSE, fPulserColor);
     1281          continue;
     1282        }
     1283     
     1284      MCalibrationChargePix &pix = (MCalibrationChargePix&)(*fCam)[i];
     1285      MGeomPix              &geo =                        (*fGeom)[i];
     1286     
     1287      const Float_t qe        = pix.GetPheFFactorMethod()
     1288                             / fBlindPixel->GetFluxInsidePlexiglass()
     1289                             / geo.GetA()
     1290                            * fQECam->GetPlexiglassQE();
     1291
     1292      const Float_t qerelvar = fBlindPixel->GetFluxInsidePlexiglassRelVar()
     1293                               + fQECam->GetPlexiglassQERelVar()
     1294                               + pix.GetPheFFactorMethodRelVar();
     1295
     1296      qepix.SetQEBlindPixel    ( qe            , fPulserColor );
     1297      qepix.SetQEBlindPixelVar ( qerelvar*qe*qe, fPulserColor );     
     1298      qepix.UpdateBlindPixelMethod();
     1299    }
     1300}
     1301
     1302// ------------------------------------------------------------------------
     1303//
     1304// Loop over pixels:
     1305//
     1306// - Continue, if not MCalibrationChargePINDiode::IsFluxOutsidePlexiglassAvailable() and set:
     1307//                    MCalibrationQEPix::SetPINDiodeMethodValid(kFALSE,fPulserColor)
     1308//
     1309// - Calculate the quantum efficiency with the formula:
     1310//
     1311//   QE =  Num.Phes / MCalibrationChargePINDiode::GetFluxOutsidePlexiglass() / MGeomPix::GetA()
     1312//
     1313// - Set QE in MCalibrationQEPix::SetQEPINDiode ( QE, fPulserColor );
     1314// - Set Variance of QE in  MCalibrationQEPix::SetQEPINDiodeVar ( Variance, fPulserColor );
     1315// - Set bit MCalibrationQEPix::SetPINDiodeMethodValid(kTRUE,fPulserColor)
     1316//
     1317// - Call MCalibrationQEPix::UpdatePINDiodeMethod()
     1318//
     1319void MCalibrationChargeCalc::FinalizePINDiodeQECam()
     1320{
     1321 
     1322  const UInt_t npixels  = fGeom->GetNumPixels();
     1323
     1324  //
     1325  //  With the knowledge of the overall photon flux, calculate the
     1326  //  quantum efficiencies after the PIN Diode method
     1327  //
     1328  for (UInt_t i=0; i<npixels; i++)
     1329    {
     1330     
     1331      MCalibrationQEPix   &qepix = (MCalibrationQEPix&)  (*fQECam)[i];
     1332
     1333      if (!fPINDiode)
     1334        {
     1335          qepix.SetPINDiodeMethodValid(kFALSE, fPulserColor);
     1336          continue;
     1337        }
     1338     
     1339      if (!fPINDiode->IsFluxOutsidePlexiglassAvailable())
     1340        {
     1341          qepix.SetPINDiodeMethodValid(kFALSE, fPulserColor);
     1342          continue;
     1343        }
     1344
     1345      MBadPixelsPix &bad  =  (*fBadPixels)[i];
     1346
     1347      if (!bad.IsUnsuitable (MBadPixelsPix::kUnsuitableRun))
     1348        {
     1349          qepix.SetPINDiodeMethodValid(kFALSE, fPulserColor);
     1350          continue;
     1351        }
     1352     
     1353      MCalibrationChargePix &pix = (MCalibrationChargePix&)(*fCam)[i];
     1354      MGeomPix              &geo =                        (*fGeom)[i];
     1355     
     1356      const Float_t qe       =  pix.GetPheFFactorMethod()
     1357                               / fPINDiode->GetFluxOutsidePlexiglass()
     1358                               / geo.GetA();
     1359
     1360      const Float_t qerelvar = fPINDiode->GetFluxOutsidePlexiglassRelVar() + pix.GetPheFFactorMethodRelVar();
     1361
     1362      qepix.SetQEPINDiode    ( qe            , fPulserColor );
     1363      qepix.SetQEPINDiodeVar ( qerelvar*qe*qe, fPulserColor );     
     1364      qepix.UpdateBlindPixelMethod();
     1365    }
     1366}
     1367
     1368// -----------------------------------------------------------------------------------------------
     1369//
     1370// Print out statistics about BadPixels of type UnsuitableType_t
     1371//
    12591372void MCalibrationChargeCalc::PrintUnsuitable(MBadPixelsPix::UnsuitableType_t typ, const char *text) const
    12601373{
     
    12781391}
    12791392
     1393// -----------------------------------------------------------------------------------------------
     1394//
     1395// Print out statistics about BadPixels of type UncalibratedType_t
     1396//
    12801397void MCalibrationChargeCalc::PrintUncalibrated(MBadPixelsPix::UncalibratedType_t typ, const char *text) const
    12811398{
Note: See TracChangeset for help on using the changeset viewer.