File indexing completed on 2025-08-12 02:29:05
0001 #include <memory>
0002
0003 #include "FWCore/Framework/interface/Frameworkfwd.h"
0004 #include "FWCore/Framework/interface/stream/EDProducer.h"
0005 #include "FWCore/Framework/interface/ConsumesCollector.h"
0006 #include "FWCore/ParameterSet/interface/ParameterSet.h"
0007 #include "FWCore/ParameterSet/interface/ParameterSetDescription.h"
0008 #include "FWCore/ParameterSet/interface/EmptyGroupDescription.h"
0009 #include "FWCore/ParameterSet/interface/allowedValues.h"
0010 #include "Utilities/General/interface/ClassName.h"
0011
0012 #include "CommonTools/Utils/interface/StringCutObjectSelector.h"
0013 #include "CommonTools/Utils/interface/StringObjectFunction.h"
0014
0015 #include "DataFormats/Common/interface/ValueMap.h"
0016 #include "DataFormats/NanoAOD/interface/FlatTable.h"
0017 #include "PhysicsTools/NanoAOD/interface/SimpleFlatTableProducer.h"
0018
0019 #include "DataFormats/L1Scouting/interface/OrbitCollection.h"
0020 #include "DataFormats/NanoAOD/interface/OrbitFlatTable.h"
0021
0022 template <typename T>
0023 class SimpleOrbitFlatTableProducer : public edm::stream::EDProducer<> {
0024 public:
0025 using TOrbitCollection = OrbitCollection<T>;
0026
0027 SimpleOrbitFlatTableProducer(edm::ParameterSet const ¶ms)
0028 : name_(params.getParameter<std::string>("name")),
0029 doc_(params.getParameter<std::string>("doc")),
0030 singleton_(params.getParameter<bool>("singleton")),
0031 extension_(params.getParameter<bool>("extension")),
0032 skipNonExistingSrc_(params.getParameter<bool>("skipNonExistingSrc")),
0033 cut_(!singleton_ ? params.getParameter<std::string>("cut") : "",
0034 !singleton_ && params.existsAs<bool>("lazyEval") ? params.getUntrackedParameter<bool>("lazyEval") : false),
0035 maxLen_(params.existsAs<unsigned int>("maxLen") ? params.getParameter<unsigned int>("maxLen")
0036 : std::numeric_limits<unsigned int>::max()),
0037 src_(consumes(params.getParameter<edm::InputTag>("src"))) {
0038
0039 edm::ParameterSet const &varsPSet = params.getParameter<edm::ParameterSet>("variables");
0040 for (const std::string &vname : varsPSet.getParameterNamesForType<edm::ParameterSet>()) {
0041 const auto &varPSet = varsPSet.getParameter<edm::ParameterSet>(vname);
0042 const std::string &type = varPSet.getParameter<std::string>("type");
0043 if (type == "int")
0044 vars_.push_back(std::make_unique<IntVar>(vname, varPSet));
0045 else if (type == "uint")
0046 vars_.push_back(std::make_unique<UIntVar>(vname, varPSet));
0047 else if (type == "int64")
0048 vars_.push_back(std::make_unique<Int64Var>(vname, varPSet));
0049 else if (type == "uint64")
0050 vars_.push_back(std::make_unique<UInt64Var>(vname, varPSet));
0051 else if (type == "float")
0052 vars_.push_back(std::make_unique<FloatVar>(vname, varPSet));
0053 else if (type == "double")
0054 vars_.push_back(std::make_unique<DoubleVar>(vname, varPSet));
0055 else if (type == "uint8")
0056 vars_.push_back(std::make_unique<UInt8Var>(vname, varPSet));
0057 else if (type == "int16")
0058 vars_.push_back(std::make_unique<Int16Var>(vname, varPSet));
0059 else if (type == "uint16")
0060 vars_.push_back(std::make_unique<UInt16Var>(vname, varPSet));
0061 else if (type == "bool")
0062 vars_.push_back(std::make_unique<BoolVar>(vname, varPSet));
0063 else
0064 throw cms::Exception("Configuration", "unsupported type " + type + " for variable " + vname);
0065 }
0066
0067
0068 if (params.existsAs<edm::ParameterSet>("externalVariables")) {
0069 edm::ParameterSet const &extvarsPSet = params.getParameter<edm::ParameterSet>("externalVariables");
0070 for (const std::string &vname : extvarsPSet.getParameterNamesForType<edm::ParameterSet>()) {
0071 const auto &varPSet = extvarsPSet.getParameter<edm::ParameterSet>(vname);
0072 const std::string &type = varPSet.getParameter<std::string>("type");
0073 if (type == "int")
0074 extvars_.push_back(
0075 std::make_unique<IntExtVar>(vname, varPSet, this->consumesCollector(), this->skipNonExistingSrc_));
0076 else if (type == "uint")
0077 extvars_.push_back(
0078 std::make_unique<UIntExtVar>(vname, varPSet, this->consumesCollector(), this->skipNonExistingSrc_));
0079 else if (type == "int64")
0080 extvars_.push_back(
0081 std::make_unique<Int64ExtVar>(vname, varPSet, this->consumesCollector(), this->skipNonExistingSrc_));
0082 else if (type == "uint64")
0083 extvars_.push_back(
0084 std::make_unique<UInt64ExtVar>(vname, varPSet, this->consumesCollector(), this->skipNonExistingSrc_));
0085 else if (type == "float")
0086 extvars_.push_back(
0087 std::make_unique<FloatExtVar>(vname, varPSet, this->consumesCollector(), this->skipNonExistingSrc_));
0088 else if (type == "double")
0089 extvars_.push_back(
0090 std::make_unique<DoubleExtVar>(vname, varPSet, this->consumesCollector(), this->skipNonExistingSrc_));
0091 else if (type == "uint8")
0092 extvars_.push_back(
0093 std::make_unique<UInt8ExtVar>(vname, varPSet, this->consumesCollector(), this->skipNonExistingSrc_));
0094 else if (type == "int16")
0095 extvars_.push_back(
0096 std::make_unique<Int16ExtVar>(vname, varPSet, this->consumesCollector(), this->skipNonExistingSrc_));
0097 else if (type == "uint16")
0098 extvars_.push_back(
0099 std::make_unique<UInt16ExtVar>(vname, varPSet, this->consumesCollector(), this->skipNonExistingSrc_));
0100 else if (type == "bool")
0101 extvars_.push_back(
0102 std::make_unique<BoolExtVar>(vname, varPSet, this->consumesCollector(), this->skipNonExistingSrc_));
0103 else
0104 throw cms::Exception("Configuration", "unsupported type " + type + " for variable " + vname);
0105 }
0106 }
0107
0108 produces<l1ScoutingRun3::OrbitFlatTable>();
0109 }
0110
0111 ~SimpleOrbitFlatTableProducer() override {}
0112
0113 static void fillDescriptions(edm::ConfigurationDescriptions &descriptions) {
0114 edm::ParameterSetDescription desc;
0115 std::string classname = ClassName<T>::name();
0116 desc.add<std::string>("name")->setComment("name of the branch in the flat table output for " + classname);
0117 desc.add<std::string>("doc", "")->setComment("few words of self documentation");
0118 desc.ifValue(
0119 edm::ParameterDescription<bool>(
0120 "singleton", false, true, edm::Comment("whether or not the input collection is single-element")),
0121 false >> (edm::ParameterDescription<std::string>(
0122 "cut", "", true, edm::Comment("selection on the main input collection")) and
0123 edm::ParameterDescription<bool>("lazyEval",
0124 false,
0125 false,
0126 edm::Comment("if true, can use methods of inheriting classes. Can "
0127 "cause problems when multi-threading."))) or
0128 true >> edm::EmptyGroupDescription());
0129
0130 desc.addOptional<unsigned int>("maxLen")->setComment(
0131 "define the maximum length per bx of the input collection to put in the branch");
0132 desc.add<bool>("extension", false)->setComment("whether or not to extend an existing same table");
0133 desc.add<bool>("skipNonExistingSrc", false)
0134 ->setComment("whether or not to skip producing the table on absent input product");
0135 desc.add<edm::InputTag>("src")->setComment("input collection to fill the flat table");
0136
0137 edm::ParameterSetDescription variable;
0138 variable.add<std::string>("expr")->setComment("a function to define the content of the branch in the flat table");
0139 variable.add<std::string>("doc")->setComment("few words description of the branch content");
0140 variable.addUntracked<bool>("lazyEval", false)
0141 ->setComment("if true, can use methods of inheriting classes in `expr`. Can cause problems with threading.");
0142 variable.ifValue(
0143 edm::ParameterDescription<std::string>(
0144 "type", "int", true, edm::Comment("the c++ type of the branch in the flat table")),
0145 edm::allowedValues<std::string>("int", "uint", "float", "double", "uint8", "int16", "uint16", "bool"));
0146 variable.addOptionalNode(
0147 edm::ParameterDescription<int>(
0148 "precision", true, edm::Comment("the precision with which to store the value in the flat table")) xor
0149 edm::ParameterDescription<std::string>(
0150 "precision", true, edm::Comment("the precision with which to store the value in the flat table")),
0151 false);
0152
0153 edm::ParameterSetDescription variables;
0154 variables.setComment("a parameters set to define all variable to fill the flat table");
0155 variables.addNode(
0156 edm::ParameterWildcard<edm::ParameterSetDescription>("*", edm::RequireZeroOrMore, true, variable));
0157 desc.add<edm::ParameterSetDescription>("variables", variables);
0158
0159
0160 edm::ParameterSetDescription extvariable;
0161 extvariable.add<edm::InputTag>("src")->setComment("valuemap input collection to fill the flat table");
0162 extvariable.add<std::string>("doc")->setComment("few words description of the branch content");
0163 extvariable.ifValue(edm::ParameterDescription<std::string>(
0164 "type", "int", true, edm::Comment("the c++ type of the branch in the flat table")),
0165 edm::allowedValues<std::string>(
0166 "int", "uint", "int64", "uint64", "float", "double", "uint8", "int16", "uint16", "bool"));
0167 extvariable.addOptionalNode(
0168 edm::ParameterDescription<int>(
0169 "precision", true, edm::Comment("the precision with which to store the value in the flat table")) xor
0170 edm::ParameterDescription<std::string>("precision",
0171 true,
0172 edm::Comment("the precision with which to store the value in the "
0173 "flat table, as a function of the object evaluated")),
0174 false);
0175
0176 edm::ParameterSetDescription extvariables;
0177 extvariables.setComment("a parameters set to define all variable taken form valuemap to fill the flat table");
0178 extvariables.addOptionalNode(
0179 edm::ParameterWildcard<edm::ParameterSetDescription>("*", edm::RequireZeroOrMore, true, extvariable), false);
0180 desc.addOptional<edm::ParameterSetDescription>("externalVariables", extvariables);
0181
0182 descriptions.addWithDefaultLabel(desc);
0183 }
0184
0185 void produce(edm::Event &iEvent, const edm::EventSetup &iSetup) override {
0186 edm::Handle<TOrbitCollection> src;
0187 iEvent.getByToken(src_, src);
0188
0189 std::vector<const T *> selobjs;
0190 std::vector<edm::Ptr<T>> selptrs;
0191 std::vector<unsigned int> selbxOffsets;
0192
0193 if (src.isValid() || !skipNonExistingSrc_) {
0194 if (singleton_) {
0195
0196 for (int i = 0; i < src->size(); i++) {
0197 selobjs.push_back(&(*src)[i]);
0198 if (!extvars_.empty())
0199 selptrs.emplace_back(src, 0);
0200 }
0201
0202
0203 selbxOffsets = src->bxOffsets();
0204
0205 } else {
0206
0207 std::vector<unsigned int> bxOffsets = src->bxOffsets();
0208
0209
0210 std::vector<unsigned int> selbxSizes = std::vector<unsigned int>(l1ScoutingRun3::OrbitFlatTable::NBX + 1, 0);
0211
0212 for (const unsigned int &bx : src->getFilledBxs()) {
0213 const auto &objs = src->bxIterator(bx);
0214 for (unsigned int i = 0; i < objs.size(); i++) {
0215 const auto &obj = objs[i];
0216 edm::Ptr<T> objptr = edm::Ptr<T>(src, bxOffsets[bx] + i);
0217 if (cut_(obj)) {
0218 selobjs.push_back(&obj);
0219 if (!extvars_.empty())
0220 selptrs.push_back(objptr);
0221 selbxSizes[bx]++;
0222 }
0223 if (selbxSizes[bx] >= maxLen_)
0224 break;
0225 }
0226 }
0227
0228 selbxOffsets = sizes2offsets(selbxSizes);
0229 }
0230 }
0231
0232 auto out = std::make_unique<l1ScoutingRun3::OrbitFlatTable>(selbxOffsets, name_, singleton_, extension_);
0233 out->setDoc(doc_);
0234
0235 for (const auto &var : this->vars_)
0236 var->fill(selobjs, *out);
0237 for (const auto &var : this->extvars_)
0238 var->fill(iEvent, selptrs, *out);
0239
0240 iEvent.put(std::move(out));
0241 }
0242
0243 private:
0244 const std::string name_;
0245 const std::string doc_;
0246 const bool singleton_;
0247 const bool extension_;
0248 const bool skipNonExistingSrc_;
0249 const StringCutObjectSelector<T> cut_;
0250 const unsigned int maxLen_;
0251 const edm::EDGetTokenT<TOrbitCollection> src_;
0252
0253
0254 typedef FuncVariable<T, StringObjectFunction<T>, int32_t> IntVar;
0255 typedef FuncVariable<T, StringObjectFunction<T>, uint32_t> UIntVar;
0256 typedef FuncVariable<T, StringObjectFunction<T>, int64_t> Int64Var;
0257 typedef FuncVariable<T, StringObjectFunction<T>, uint64_t> UInt64Var;
0258 typedef FuncVariable<T, StringObjectFunction<T>, float> FloatVar;
0259 typedef FuncVariable<T, StringObjectFunction<T>, double> DoubleVar;
0260 typedef FuncVariable<T, StringObjectFunction<T>, uint8_t> UInt8Var;
0261 typedef FuncVariable<T, StringObjectFunction<T>, int16_t> Int16Var;
0262 typedef FuncVariable<T, StringObjectFunction<T>, uint16_t> UInt16Var;
0263 typedef FuncVariable<T, StringCutObjectSelector<T>, bool> BoolVar;
0264 std::vector<std::unique_ptr<Variable<T>>> vars_;
0265
0266
0267 typedef ValueMapVariable<T, int32_t> IntExtVar;
0268 typedef ValueMapVariable<T, uint32_t> UIntExtVar;
0269 typedef ValueMapVariable<T, int64_t> Int64ExtVar;
0270 typedef ValueMapVariable<T, uint64_t> UInt64ExtVar;
0271 typedef ValueMapVariable<T, float> FloatExtVar;
0272 typedef ValueMapVariable<T, double, float> DoubleExtVar;
0273 typedef ValueMapVariable<T, bool> BoolExtVar;
0274 typedef ValueMapVariable<T, int, uint8_t> UInt8ExtVar;
0275 typedef ValueMapVariable<T, int, int16_t> Int16ExtVar;
0276 typedef ValueMapVariable<T, int, uint16_t> UInt16ExtVar;
0277 std::vector<std::unique_ptr<ExtVariable<T>>> extvars_;
0278
0279 private:
0280 std::vector<unsigned int> sizes2offsets(std::vector<unsigned int> sizes) const {
0281 std::vector<unsigned int> offsets(sizes.size() + 1, 0);
0282 for (unsigned int i = 0; i < sizes.size(); i++) {
0283 offsets[i + 1] = offsets[i] + sizes[i];
0284 }
0285 return offsets;
0286 }
0287 };
0288
0289 #include "DataFormats/L1Scouting/interface/L1ScoutingMuon.h"
0290 typedef SimpleOrbitFlatTableProducer<l1ScoutingRun3::Muon> SimpleL1ScoutingMuonOrbitFlatTableProducer;
0291
0292 #include "DataFormats/L1Scouting/interface/L1ScoutingCalo.h"
0293 typedef SimpleOrbitFlatTableProducer<l1ScoutingRun3::EGamma> SimpleL1ScoutingEGammaOrbitFlatTableProducer;
0294 typedef SimpleOrbitFlatTableProducer<l1ScoutingRun3::Tau> SimpleL1ScoutingTauOrbitFlatTableProducer;
0295 typedef SimpleOrbitFlatTableProducer<l1ScoutingRun3::Jet> SimpleL1ScoutingJetOrbitFlatTableProducer;
0296
0297 #include "DataFormats/L1Scouting/interface/L1ScoutingBMTFStub.h"
0298 typedef SimpleOrbitFlatTableProducer<l1ScoutingRun3::BMTFStub> SimpleL1ScoutingBMTFStubOrbitFlatTableProducer;
0299
0300 #include "FWCore/Framework/interface/MakerMacros.h"
0301 DEFINE_FWK_MODULE(SimpleL1ScoutingMuonOrbitFlatTableProducer);
0302 DEFINE_FWK_MODULE(SimpleL1ScoutingEGammaOrbitFlatTableProducer);
0303 DEFINE_FWK_MODULE(SimpleL1ScoutingTauOrbitFlatTableProducer);
0304 DEFINE_FWK_MODULE(SimpleL1ScoutingJetOrbitFlatTableProducer);
0305 DEFINE_FWK_MODULE(SimpleL1ScoutingBMTFStubOrbitFlatTableProducer);