Back to home page

Project CMSSW displayed by LXR

 
 

    


File indexing completed on 2024-04-06 12:21:33

0001 #include <iostream>
0002 #include "L1Trigger/Phase2L1ParticleFlow/interface/taus/TauNNIdHW.h"
0003 
0004 TauNNIdHW::TauNNIdHW() { NNvectorVar_.clear(); }
0005 TauNNIdHW::~TauNNIdHW() {}
0006 
0007 void TauNNIdHW::initialize(const std::string &iInput, int iNParticles) {
0008   fNParticles_ = iNParticles;
0009   fPt_ = std::make_unique<pt_t[]>(fNParticles_);
0010   fEta_ = std::make_unique<etaphi_t[]>(fNParticles_);
0011   fPhi_ = std::make_unique<etaphi_t[]>(fNParticles_);
0012   fId_ = std::make_unique<id_t[]>(fNParticles_);
0013   fInput_ = iInput;
0014 }
0015 
0016 //Prepare the inputs for the Tau NN
0017 void TauNNIdHW::SetNNVectorVar() {
0018   NNvectorVar_.clear();
0019   for (unsigned i0 = 0; i0 < fNParticles_; i0++) {
0020     input_t pPt = input_t(fPt_.get()[i0]);
0021     input_t pEta = input_t(fEta_.get()[i0]);
0022     input_t pPhi = input_t(fPhi_.get()[i0]);
0023 
0024     NNvectorVar_.push_back(pPt);
0025     NNvectorVar_.push_back(pEta);
0026     NNvectorVar_.push_back(pPhi);
0027     if (fPt_.get()[i0] == 0) {
0028       for (unsigned i1 = 0; i1 < 5; i1++)
0029         NNvectorVar_.push_back(0);
0030       continue;
0031     }
0032     NNvectorVar_.push_back(fId_.get()[i0] == l1t::PFCandidate::Photon);         // Photon
0033     NNvectorVar_.push_back(fId_.get()[i0] == l1t::PFCandidate::Electron);       // Electron
0034     NNvectorVar_.push_back(fId_.get()[i0] == l1t::PFCandidate::Muon);           // Muon
0035     NNvectorVar_.push_back(fId_.get()[i0] == l1t::PFCandidate::NeutralHadron);  // Neutral Had
0036     NNvectorVar_.push_back(fId_.get()[i0] == l1t::PFCandidate::ChargedHadron);  // Charged Had
0037   }
0038 }
0039 
0040 // Main architecture of the NN here
0041 Tau_NN_Result TauNNIdHW::EvaluateNN() {
0042   input_t model_input[N_INPUT_1_1];
0043   for (unsigned int i = 0; i < NNvectorVar_.size(); i++) {
0044     model_input[i] = input_t(NNvectorVar_[i]);
0045   }
0046 
0047   layer2_t layer2_out[N_LAYER_2];
0048   nnet::dense<input_t, layer2_t, config2>(model_input, layer2_out, w2, b2);  // Dense_1
0049 
0050   layer4_t layer4_out[N_LAYER_2];
0051   nnet::relu<layer2_t, layer4_t, relu_config4>(layer2_out, layer4_out);  // relu_1
0052 
0053   layer5_t layer5_out[N_LAYER_5];
0054   nnet::dense<layer4_t, layer5_t, config5>(layer4_out, layer5_out, w5, b5);  // Dense_2
0055 
0056   layer7_t layer7_out[N_LAYER_5];
0057   nnet::relu<layer5_t, layer7_t, relu_config7>(layer5_out, layer7_out);  // relu_2
0058 
0059   layer8_t layer8_out[N_LAYER_8];
0060   nnet::dense<layer7_t, layer8_t, config8>(layer7_out, layer8_out, w8, b8);  // Dense_3
0061 
0062   layer10_t layer10_out[N_LAYER_8];
0063   nnet::relu<layer8_t, layer10_t, relu_config10>(layer8_out, layer10_out);  // relu_3
0064 
0065   layer11_t layer11_out[N_LAYER_11];
0066   nnet::dense<layer10_t, layer11_t, config11>(layer10_out, layer11_out, w11, b11);  // Dense_4
0067 
0068   layer13_t layer13_out[N_LAYER_11];
0069   nnet::relu<layer11_t, layer13_t, relu_config13>(layer11_out, layer13_out);  // relu_4
0070 
0071   layer14_t layer14_out[N_LAYER_14];
0072   nnet::dense<layer13_t, layer14_t, config14>(layer13_out, layer14_out, w14, b14);  // Dense_5
0073 
0074   layer16_t layer16_out[N_LAYER_14];
0075   nnet::relu<layer14_t, layer16_t, relu_config16>(layer14_out, layer16_out);  // relu_5
0076 
0077   layer17_t layer17_out[N_LAYER_17];
0078   nnet::dense<layer16_t, layer17_t, config17>(layer16_out, layer17_out, w17, b17);  // Dense_6
0079 
0080   result_t layer19_out[N_LAYER_17];
0081   nnet::sigmoid<layer17_t, result_t, sigmoid_config19>(layer17_out, layer19_out);  // jetID_output
0082 
0083   result_t layer20_out[N_LAYER_20];
0084   nnet::dense<layer16_t, result_t, config20>(layer16_out, layer20_out, w20, b20);  // pT_output
0085 
0086   // Return both pT correction and the NN ID
0087   Tau_NN_Result nn_out;
0088   nn_out.nn_pt_correction = layer20_out[0];
0089   nn_out.nn_id = layer19_out[0];
0090 
0091   return nn_out;
0092 }
0093 
0094 /*
0095 // Uncomment for debugging purposes
0096 void TauNNIdHW::print() { 
0097   for (unsigned i0 = 0; i0 < fNParticles_; i0++) {
0098     input_t pPt  = input_t(fPt_.get()[i0]);
0099     input_t pEta = input_t(fEta_.get()[i0]);
0100     input_t pPhi = input_t(fPhi_.get()[i0]);
0101     input_t pId  = input_t(fId_.get()[i0]);    
0102     fprintf(file_, " %08x", pPt.to_uint());
0103     fprintf(file_, " %08x", pEta.to_uint());
0104     fprintf(file_, " %08x", pPhi.to_uint());
0105     fprintf(file_, " %08x", pId.to_uint());
0106   }
0107   fprintf(file_, "\n");
0108 }
0109 */
0110 
0111 Tau_NN_Result TauNNIdHW::compute(const l1t::PFCandidate &iSeed, std::vector<l1t::PFCandidate> &iParts) {
0112   // Initialize the input vector
0113   for (unsigned i0 = 0; i0 < fNParticles_; i0++) {
0114     fPt_.get()[i0] = 0.;
0115     fEta_.get()[i0] = 0.;
0116     fPhi_.get()[i0] = 0.;
0117     fId_.get()[i0] = 0.;
0118   }
0119 
0120   // Sort the candidates by pT
0121   std::sort(iParts.begin(), iParts.end(), [](l1t::PFCandidate i, l1t::PFCandidate j) {
0122     return (pt_t(i.pt()) > pt_t(j.pt()));
0123   });
0124 
0125   // Compute the values w.r.t to the seeds
0126   for (unsigned int i0 = 0; i0 < iParts.size(); i0++) {
0127     if (i0 >= fNParticles_)
0128       break;
0129 
0130     fPt_.get()[i0] = pt_t(iParts[i0].pt());
0131     fEta_.get()[i0] = etaphi_t(iSeed.eta() - iParts[i0].eta());
0132     etaphi_t lDPhi = etaphi_t(iSeed.phi()) - etaphi_t(iParts[i0].phi());
0133     etaphi_t lMPI = 3.1415;
0134 
0135     if (lDPhi > lMPI)
0136       lDPhi = lDPhi - lMPI;
0137     if (lDPhi < -lMPI)
0138       lDPhi = lDPhi + lMPI;
0139 
0140     fPhi_.get()[i0] = lDPhi;
0141     fId_.get()[i0] = id_t(iParts[i0].id());
0142   }
0143 
0144   // Set the inputs
0145   SetNNVectorVar();
0146 
0147   // Return the N outputs with the inputs
0148   return EvaluateNN();
0149 }