ExpressionTreeNode CustomHbondForceImpl::replaceFunctions(const ExpressionTreeNode& node, map<string, int> atoms, map<string, vector<int> >& distances, map<string, vector<int> >& angles, map<string, vector<int> >& dihedrals, set<string>& variables) { const Operation& op = node.getOperation(); if (op.getId() == Operation::VARIABLE && variables.find(op.getName()) == variables.end()) throw OpenMMException("CustomHBondForce: Unknown variable '"+op.getName()+"'"); if (op.getId() != Operation::CUSTOM || op.getNumArguments() < 2) { // This is not an angle or dihedral, so process its children. vector<ExpressionTreeNode> children; for (int i = 0; i < (int) node.getChildren().size(); i++) children.push_back(replaceFunctions(node.getChildren()[i], atoms, distances, angles, dihedrals, variables)); return ExpressionTreeNode(op.clone(), children); } const Operation::Custom& custom = static_cast<const Operation::Custom&>(op); // Identify the atoms this term is based on. int numArgs = custom.getNumArguments(); vector<int> indices(numArgs); for (int i = 0; i < numArgs; i++) { map<string, int>::const_iterator iter = atoms.find(node.getChildren()[i].getOperation().getName()); if (iter == atoms.end()) throw OpenMMException("CustomHBondForce: Unknown particle '"+node.getChildren()[i].getOperation().getName()+"'"); indices[i] = iter->second; } // Select a name for the variable and add it to the appropriate map. stringstream variable; if (numArgs == 2) variable << "distance"; else if (numArgs == 3) variable << "angle"; else variable << "dihedral"; for (int i = 0; i < numArgs; i++) variable << indices[i]; string name = variable.str(); if (numArgs == 2) distances[name] = indices; else if (numArgs == 3) angles[name] = indices; else dihedrals[name] = indices; // Return a new node that represents it as a simple variable. return ExpressionTreeNode(new Operation::Variable(name)); }
ParsedExpression CustomHbondForceImpl::prepareExpression(const CustomHbondForce& force, const map<string, CustomFunction*>& customFunctions, map<string, vector<int> >& distances, map<string, vector<int> >& angles, map<string, vector<int> >& dihedrals) { CustomHbondForceImpl::FunctionPlaceholder custom(1); CustomHbondForceImpl::FunctionPlaceholder distance(2); CustomHbondForceImpl::FunctionPlaceholder angle(3); CustomHbondForceImpl::FunctionPlaceholder dihedral(4); map<string, CustomFunction*> functions = customFunctions; functions["distance"] = &distance; functions["angle"] = ∠ functions["dihedral"] = &dihedral; ParsedExpression expression = Lepton::Parser::parse(force.getEnergyFunction(), functions); map<string, int> atoms; atoms["a1"] = 0; atoms["a2"] = 1; atoms["a3"] = 2; atoms["d1"] = 3; atoms["d2"] = 4; atoms["d3"] = 5; set<string> variables; for (int i = 0; i < force.getNumPerDonorParameters(); i++) variables.insert(force.getPerDonorParameterName(i)); for (int i = 0; i < force.getNumPerAcceptorParameters(); i++) variables.insert(force.getPerAcceptorParameterName(i)); for (int i = 0; i < force.getNumGlobalParameters(); i++) variables.insert(force.getGlobalParameterName(i)); return ParsedExpression(replaceFunctions(expression.getRootNode(), atoms, distances, angles, dihedrals, variables)).optimize(); }
std::vector<Doublet> WLeptonic::ReconstructNeutrino(Lepton const &lepton, Vector2<Momentum> const &missing_et) const { INFO0; auto linear_term = (sqr(MassOf(Id::W)) - lepton.MassSquare()) / 2. + missing_et * lepton.Transverse(); auto lepton_pz_square = sqr(lepton.Pz()); auto lepton_square = sqr(lepton.Energy()) - lepton_pz_square; auto radicant = lepton_pz_square * (sqr(linear_term) - lepton_square * sqr(missing_et)); if (radicant < 0_eV * eV * eV2 * eV2) { INFO("Imaginary root", "move missing et towards lepton"); auto reco = missing_et + 0.1 * (lepton.Transverse() - missing_et); return ReconstructNeutrino(lepton, reco); } CHECK(radicant != 0_eV * eV * eV2 * eV2, "Radicant exactly zero", "implement this case!"); auto sqrt = boost::units::sqrt(radicant); auto neutrino_1_e = (lepton.Energy() * linear_term - sqrt) / lepton_square; auto neutrino_1_pz = (lepton_pz_square * linear_term - lepton.Energy() * sqrt) / lepton.Pz() / lepton_square; auto neutrino_1 = Lepton {missing_et, neutrino_1_pz, neutrino_1_e}; auto neutrino_2_e = (lepton.Energy() * linear_term + sqrt) / lepton_square; auto neutrino_2_pz = (lepton_pz_square * linear_term + lepton.Energy() * sqrt) / lepton.Pz() / lepton_square; auto neutrino_2 = Lepton {missing_et, neutrino_2_pz, neutrino_2_e}; return {Doublet(lepton, neutrino_1), Doublet(lepton, neutrino_2)}; }
void ClosestLepton::AddLepton(const Lepton& lepton) { INFO0; if (Close<Lepton>(lepton)(jet_) && lepton.Pt() > Pt()) lepton_ = lepton; }
void ChargedHiggsTauNu::analyzeGen(Event*e, string systname) { // no systematics shifts for this if (systname !="" and systname != "NONE") return; string label = GetLabel(e); Weight* w = e->GetWeight(); // make sure we don't book sf or corrections here double mcWeight=w->GetBareMCWeight() * w->GetBarePUWeight()* w->GetBareMCXsec() * w->GetBareLumi() / w->GetBareNevents(); Fill("ChargedHiggsTauNu/Gen/CutFlow_"+label,systname,0,mcWeight); // find the H+ int iHpm=-1; int iTau=-1; int iLFromTau=-1; // find leptonic taus int iIsoL = -1; // is there an isolated lepton ? for(unsigned i = 0 ; ;++i) { GenParticle *g = e->GetGenParticle(i); if (g==NULL) break; //exit condition int apdg = abs(g->GetPdgId()); if (iHpm <0 and apdg == 37 ) { iHpm = i; } if (iTau <0 and apdg == 15 ) { iTau = i; } if (iLFromTau <0 and (apdg == 11 or apdg == 13) and e->GenParticleDecayedFrom(i,15) ) { iLFromTau = i; } if (iIsoL <0 and (apdg == 11 or apdg == 13) and g->IsPromptFinalState() and g->Pt() >10 and abs(g->Eta())<2.4){ float iso = 0.0; for(unsigned j = 0 ; ;++j) { if (i == j ) continue; // no double counting; GenParticle *g2 = e->GetGenParticle(j); if (g2 == NULL) break; if (not g2->IsPromptFinalState()) continue; if (g2->IsDressed() ) continue; // no dressed leptons if (g2->DeltaR(g) >0.1) continue; iso += g2->Pt(); } if (iso<10) iIsoL = i; } } bool lepVeto=false; if (e->Nleps() ==0 ) lepVeto=true; else if( e->GetMuon(0) == NULL){ // no 10 GeV muon if (e->GetElectron(0) !=NULL and e->GetElectron(0)->Pt() <15) lepVeto=true; // pt ordered } vector<Lepton*> miniIsoLeptons; bool lepVetoMiniIso=true; for(unsigned il=0 ; ;++il) { Lepton *l = e->GetBareLepton(il); if (l == NULL) break; // exit strategy // selection if (l->Pt() <10 ) continue; //l->SetIsoRelCut(0.25); if (abs(l->Eta()) >2.4) continue; //medium id if( not l->GetMediumId() ) continue; //MINI-ISO if( l->MiniIsolation() >0.4 ) continue;//loose // for muons require tracker and global if (l->IsMuonDirty() and not l->GetTrackerMuon()) continue; if (l->IsMuonDirty() and not l->GetGlobalMuon()) continue; // selected leptons miniIsoLeptons.push_back(l); lepVetoMiniIso=false; } // sort miniIsoLeptons by pt std::sort(miniIsoLeptons.begin(),miniIsoLeptons.end(),[](Lepton const *a, Lepton const *b ){return a->Pt() > b->Pt();}); if (iHpm >=0 ) Fill("ChargedHiggsTauNu/Gen/CutFlow_"+label,systname,1,mcWeight); if (iHpm >=0 and iTau>=0 ) Fill("ChargedHiggsTauNu/Gen/CutFlow_"+label,systname,2,mcWeight); if (iHpm >=0 and iTau>=0 and iLFromTau<0){ Fill("ChargedHiggsTauNu/Gen/CutFlow_"+label,systname,3,mcWeight); if (iIsoL <0) Fill("ChargedHiggsTauNu/Gen/CutFlow_"+label,systname,4,mcWeight); if (lepVeto) Fill("ChargedHiggsTauNu/Gen/CutFlow_"+label,systname,5,mcWeight); if (lepVetoMiniIso ) Fill("ChargedHiggsTauNu/Gen/CutFlow_"+label,systname,6,mcWeight); } }