Skip to content
Snippets Groups Projects

Calo-track monitoring

Merged Maarten Van Veghel requested to merge mveghel-calomonitoring into master
Files
2
/*****************************************************************************\
* (c) Copyright 2000-2018 CERN for the benefit of the LHCb Collaboration *
* *
* This software is distributed under the terms of the GNU General Public *
* Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING". *
* *
* In applying this licence, CERN does not waive the privileges and immunities *
* granted to it by virtue of its status as an Intergovernmental Organization *
* or submit itself to any jurisdiction. *
\*****************************************************************************/
#include "CaloDet/DeCalorimeter.h"
#include "CaloFutureUtils/TrackUtils.h"
#include "DetDesc/GenericConditionAccessorHolder.h"
#include "Event/CaloChargedInfo.h"
#include "Event/CaloClusters_v2.h"
#include "Event/Track_v3.h"
#include "Gaudi/Accumulators/Histogram.h"
#include "GaudiKernel/SystemOfUnits.h"
#include "LHCbAlgs/Consumer.h"
namespace LHCb::Calo {
namespace {
using Tracks = LHCb::Event::v3::Tracks;
using ChargedPID = LHCb::Event::Calo::v2::ChargedPID;
using BremInfo = LHCb::Event::Calo::v2::BremInfo;
using Clusters = LHCb::Event::Calo::v2::Clusters;
} // namespace
class ChargedPIDsMonitor final
: public LHCb::Algorithm::Consumer<void( Tracks const&, ChargedPID const&, BremInfo const&, Clusters const&,
DeCalorimeter const& ),
LHCb::DetDesc::usesConditions<DeCalorimeter>> {
public:
using base_type = LHCb::Algorithm::Consumer<void( Tracks const&, ChargedPID const&, BremInfo const&,
Clusters const&, DeCalorimeter const& ),
LHCb::DetDesc::usesConditions<DeCalorimeter>>;
using KeyValue = base_type::KeyValue;
// standard constructor
ChargedPIDsMonitor( std::string const& name, ISvcLocator* pSvc )
: base_type{name,
pSvc,
{KeyValue{"Tracks", ""}, KeyValue{"ChargedPID", ""}, KeyValue{"BremInfo", ""},
KeyValue{"Clusters", ""}, KeyValue{"Detector", DeCalorimeterLocation::Ecal}}} {}
// main execution
void operator()( Tracks const&, ChargedPID const&, BremInfo const&, Clusters const&,
DeCalorimeter const& ) const override;
private:
// properties
Gaudi::Property<bool> m_cluster_track_residuals{this, "ClusterTrackResiduals", true,
"Add cluster-track residual histograms"};
//// histograms ////
using Hist1F = Gaudi::Accumulators::Histogram<1, Gaudi::Accumulators::atomicity::full, float>;
using EffCounter = Gaudi::Accumulators::BinomialCounter<>;
using AxisF = Gaudi::Accumulators::Axis<float>;
// track - cluster matching
float max_res_dist = 120.f;
mutable Hist1F m_histos_clust_chi2{this, "ClustChi2", "Chi2 of track - cluster (Ecal) matching",
AxisF{301, -0.1f, 30.f}};
mutable Hist1F m_histos_cls_trk_res_x{this, "ClsTrkResidual_x", "Residual in x of cluster versus track position",
AxisF{240, -max_res_dist, max_res_dist}};
mutable Hist1F m_histos_cls_trk_res_y{this, "ClsTrkResidual_y", "Residual in y of cluster versus track position",
AxisF{240, -max_res_dist, max_res_dist}};
// electron pid ecal
mutable EffCounter m_counter_inecal{this, "InEcalAcc"};
mutable EffCounter m_counter_hasecale{this, "HasEcalEnergy"};
mutable Hist1F m_histos_eop_ecal{this, "EoverP_Ecal", "E (Ecal) over (track) momentum", AxisF{204, -0.04f, 2.f}};
mutable Hist1F m_histos_eop_ecal_hasbrem{this, "EoverP_Ecal_hasbrem",
"E (Ecal) over (track) momentum (with HasBrem)", AxisF{204, -0.04f, 2.f}};
mutable Hist1F m_histos_eshowerdll{
this, "ElectronShowerDLL",
"DLL of electron versus pion using per-cell E / p (with track-based energy estimation)",
AxisF{250, -15.f, 10.f}};
// hcal
mutable EffCounter m_counter_inhcal{this, "InHcalAcc"};
mutable EffCounter m_counter_hashcale{this, "HasHcalEnergy"};
mutable Hist1F m_histos_eop_hcal{this, "EoverP_Hcal", "E (Hcal) over (track) momentum", AxisF{204, -0.04f, 2.f}};
// brem related
mutable EffCounter m_counter_inbrem{this, "InBremAcc"};
mutable EffCounter m_counter_hasbrem{this, "HasBrem"};
mutable Hist1F m_histos_bremchi2{this, "BremChi2", "Chi2 of photon cluster vs track extrapolation under brem hypo",
AxisF{124, -0.1f, 6.1f}};
mutable Hist1F m_histos_brempide{this, "BremPIDe", "BremPIDe", AxisF{150, -2.5f, 5.f}};
mutable Hist1F m_histos_bremeop{this, "BremEoverP", "BremEnergy / (BremEnergy + p (track))",
AxisF{120, -0.1f, 1.1f}};
};
DECLARE_COMPONENT_WITH_ID( ChargedPIDsMonitor, "CaloChargedPIDsMonitor" )
//// implentation ////
// main execution
void ChargedPIDsMonitor::operator()( Tracks const& tracks, ChargedPID const& cpids, BremInfo const& brems,
Clusters const& clusters, DeCalorimeter const& calo ) const {
// do we have the right tracks?
auto stateloc = TrackUtils::extrapolation_stateloc( tracks );
if ( !stateloc.has_value() )
throw GaudiException( "Not a valid track type for this monitor", "LHCb::Event::Enum::Track::Type",
StatusCode::FAILURE );
// zip over tracks, pids and brems together
auto pids = LHCb::Event::make_zip<SIMDWrapper::InstructionSet::Scalar>( tracks, cpids, brems );
for ( auto const& pid : pids ) {
// acceptances and efficiencies
bool inecal = pid.InEcal().cast();
bool inhcal = pid.InHcal().cast();
bool inbrem = pid.InBrem().cast();
bool hasbrem = pid.HasBrem().cast();
m_counter_inecal += inecal;
m_counter_inhcal += inhcal;
m_counter_inbrem += inbrem;
m_counter_hasbrem += hasbrem;
// track-cluster matching
auto cluschi2 = pid.ClusterMatch().cast();
if ( inecal ) ++( m_histos_clust_chi2 )[cluschi2];
if ( m_cluster_track_residuals ) {
// search matched cluster
auto clusteridx = pid.ClusterIndex().cast();
if ( clusteridx >= 0 ) {
auto cluster = clusters.scalar()[clusteridx];
// cluster info
auto cls_pos = cluster->position();
// track info
LHCb::StateVector trk_state;
TrackUtils::propagateToCalo( trk_state, pid.state( stateloc.value() ), calo.plane( CaloPlane::Middle ) );
// residuals
auto res_x = cls_pos.x() - trk_state.x();
auto res_y = cls_pos.y() - trk_state.y();
++( m_histos_cls_trk_res_x )[res_x];
++( m_histos_cls_trk_res_y )[res_y];
}
}
// electron pid ecal
auto eop_ecal = pid.ElectronShowerEoP().cast();
bool hasecale = eop_ecal > 0.f;
m_counter_hasecale += hasecale;
if ( inecal && hasecale ) {
++( m_histos_eop_ecal )[eop_ecal];
++( m_histos_eshowerdll )[pid.ElectronShowerDLL().cast()];
if ( hasbrem ) ++( m_histos_eop_ecal_hasbrem )[eop_ecal];
}
// hcal
auto eop_hcal = pid.HcalEoP().cast();
bool hashcale = eop_hcal > 0.f;
m_counter_hashcale += hashcale;
if ( inhcal && hashcale ) ++( m_histos_eop_hcal )[eop_hcal];
// brem related
if ( inbrem && hasbrem ) {
auto bremchi2 = pid.BremHypoMatch();
auto brempide = pid.BremPIDe();
auto breme = pid.BremEnergy();
auto bremeop = breme / ( breme + pid.p( stateloc.value() ) );
++( m_histos_brempide )[brempide.cast()];
++( m_histos_bremchi2 )[bremchi2.cast()];
++( m_histos_bremeop )[bremeop.cast()];
}
}
return;
}
} // namespace LHCb::Calo
Loading