FastJet  3.1.0-beta.1
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Groups Pages
JetDefinition.hh
1 #ifndef __FASTJET_JETDEFINITION_HH__
2 #define __FASTJET_JETDEFINITION_HH__
3 
4 //FJSTARTHEADER
5 // $Id: JetDefinition.hh 3523 2014-08-02 13:15:21Z salam $
6 //
7 // Copyright (c) 2005-2014, Matteo Cacciari, Gavin P. Salam and Gregory Soyez
8 //
9 //----------------------------------------------------------------------
10 // This file is part of FastJet.
11 //
12 // FastJet is free software; you can redistribute it and/or modify
13 // it under the terms of the GNU General Public License as published by
14 // the Free Software Foundation; either version 2 of the License, or
15 // (at your option) any later version.
16 //
17 // The algorithms that underlie FastJet have required considerable
18 // development. They are described in the original FastJet paper,
19 // hep-ph/0512210 and in the manual, arXiv:1111.6097. If you use
20 // FastJet as part of work towards a scientific publication, please
21 // quote the version you use and include a citation to the manual and
22 // optionally also to hep-ph/0512210.
23 //
24 // FastJet is distributed in the hope that it will be useful,
25 // but WITHOUT ANY WARRANTY; without even the implied warranty of
26 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
27 // GNU General Public License for more details.
28 //
29 // You should have received a copy of the GNU General Public License
30 // along with FastJet. If not, see <http://www.gnu.org/licenses/>.
31 //----------------------------------------------------------------------
32 //FJENDHEADER
33 
34 #include<cassert>
35 #include "fastjet/internal/numconsts.hh"
36 #include "fastjet/PseudoJet.hh"
37 #include<string>
38 #include<memory>
39 
40 FASTJET_BEGIN_NAMESPACE // defined in fastjet/internal/base.hh
41 
42 /// return a string containing information about the release
43 // NB: (implemented in ClusterSequence.cc but defined here because
44 // this is a visible location)
45 std::string fastjet_version_string();
46 
47 //======================================================================
48 /// the various options for the algorithmic strategy to adopt in
49 /// clustering events with kt and cambridge style algorithms.
50 enum Strategy {
51  /// Like N2MHTLazy9 in a number of respects, but does not calculate
52  /// ghost-ghost distances and so does not carry out ghost-ghost
53  /// recombination.
54  ///
55  /// If you want active ghosted areas, then this is only suitable for
56  /// use with the anti-kt algorithm (or genkt with negative p), and
57  /// does not produce any pure ghost jets. If used with active areas
58  /// with Kt or Cam algorithms it will actually produce a passive
59  /// area.
60  ///
61  /// Particles are deemed to be ghosts if their pt is below a
62  /// threshold (currently 1e-50, hard coded as ghost_limit in
63  /// LazyTiling9SeparateGhosts).
64  ///
65  /// Currently for events with a couple of thousand normal particles
66  /// and O(10k) ghosts, this can be quicker than N2MHTLazy9, which
67  /// would otherwise be the best strategy.
68  ///
69  /// New in FJ3.1
71  /// only looks into a neighbouring tile for a particle's nearest
72  /// neighbour (NN) if that particle's in-tile NN is further than the
73  /// distance to the edge of the neighbouring tile. Uses tiles of
74  /// size R and a 3x3 tile grid around the particle.
75  /// New in FJ3.1
76  N2MHTLazy9 = -7,
77  /// Similar to N2MHTLazy9, but uses tiles of size R/2 and a 5x5 tile
78  /// grid around the particle.
79  /// New in FJ3.1
80  N2MHTLazy25 = -6,
81  /// Like to N2MHTLazy9 but uses slightly different optimizations,
82  /// e.g. for calculations of distance to nearest tile; as of
83  /// 2014-07-18 it is slightly slower and not recommended for
84  /// production use. To considered deprecated.
85  /// New in FJ3.1
87  /// faster that N2Tiled above about 500 particles; differs from it
88  /// by retainig the di(closest j) distances in a MinHeap (sort of
89  /// priority queue) rather than a simple vector.
91  /// fastest from about 50..500
92  N2Tiled = -3,
93  /// legacy
94  N2PoorTiled = -2,
95  /// fastest below 50
96  N2Plain = -1,
97  /// worse even than the usual N^3 algorithms
98  N3Dumb = 0,
99  /// automatic selection of the best (based on N), including
100  /// the LazyTiled strategies that are new to FJ3.1
101  Best = 1,
102  /// best of the NlnN variants -- best overall for N>10^4.
103  /// (Does not work for R>=2pi)
104  NlnN = 2,
105  /// legacy N ln N using 3pi coverage of cylinder.
106  /// (Does not work for R>=2pi)
107  NlnN3pi = 3,
108  /// legacy N ln N using 4pi coverage of cylinder
109  NlnN4pi = 4,
110  /// Chan's closest pair method (in a variant with 4pi coverage),
111  /// for use exclusively with the Cambridge algorithm.
112  /// (Does not work for R>=2pi)
114  /// Chan's closest pair method (in a variant with 2pi+2R coverage),
115  /// for use exclusively with the Cambridge algorithm.
116  /// (Does not work for R>=2pi)
118  /// Chan's closest pair method (in a variant with 2pi+minimal extra
119  /// variant), for use exclusively with the Cambridge algorithm.
120  /// (Does not work for R>=2pi)
121  NlnNCam = 12, // 2piMultD
122  /// the automatic strategy choice that was being made in FJ 3.0
123  /// (restricted to strategies that were present in FJ 3.0)
124  BestFJ30 = 21,
125  /// the plugin has been used...
127 };
128 
129 
130 //======================================================================
131 /// \enum JetAlgorithm
132 /// the various families of jet-clustering algorithm
133 //
134 // [Remember to update the "is_spherical()" routine if any further
135 // spherical algorithms are added to the list below]
137  /// the longitudinally invariant kt algorithm
139  /// the longitudinally invariant variant of the cambridge algorithm
140  /// (aka Aachen algoithm).
142  /// like the k_t but with distance measures
143  /// dij = min(1/kti^2,1/ktj^2) Delta R_{ij}^2 / R^2
144  /// diB = 1/kti^2
146  /// like the k_t but with distance measures
147  /// dij = min(kti^{2p},ktj^{2p}) Delta R_{ij}^2 / R^2
148  /// diB = 1/kti^{2p}
149  /// where p = extra_param()
151  /// a version of cambridge with a special distance measure for
152  /// particles whose pt is < extra_param(); this is not usually
153  /// intended for end users, but is instead automatically selected
154  /// when requesting a passive Cambridge area.
156  /// a version of genkt with a special distance measure for particles
157  /// whose pt is < extra_param() [relevant for passive areas when p<=0]
158  /// ***** NB: THERE IS CURRENTLY NO IMPLEMENTATION FOR THIS ALG *******
160  //.................................................................
161  /// the e+e- kt algorithm
163  /// the e+e- genkt algorithm (R > 2 and p=1 gives ee_kt)
165  //.................................................................
166  /// any plugin algorithm supplied by the user
168  //.................................................................
169  /// the value for the jet algorithm in a JetDefinition for which
170  /// no algorithm has yet been defined
172 };
173 
174 /// make standard Les Houches nomenclature JetAlgorithm (algorithm is general
175 /// recipe without the parameters) backward-compatible with old JetFinder
177 
178 /// provide other possible names for the Cambridge/Aachen algorithm
180 const JetAlgorithm cambridge_aachen_algorithm = cambridge_algorithm;
181 
182 //======================================================================
183 /// the various recombination schemes
185  /// summing the 4-momenta
187  /// pt weighted recombination of y,phi (and summing of pt's)
188  /// with preprocessing to make things massless by rescaling E=|\vec p|
190  /// pt^2 weighted recombination of y,phi (and summing of pt's)
191  /// with preprocessing to make things massless by rescaling E=|\vec p|
193  /// pt weighted recombination of y,phi (and summing of pt's)
194  /// with preprocessing to make things massless by rescaling |\vec p|->=E
196  /// pt^2 weighted recombination of y,phi (and summing of pt's)
197  /// with preprocessing to make things massless by rescaling |\vec p|->=E
199  /// pt weighted recombination of y,phi (and summing of pt's), with
200  /// no preprocessing
202  /// pt^2 weighted recombination of y,phi (and summing of pt's)
203  /// no preprocessing
205  /// for the user's external scheme
207 };
208 
209 
210 
211 // forward declaration, needed in order to specify interface for the
212 // plugin.
213 class ClusterSequence;
214 
215 
216 
217 
218 //======================================================================
219 /// @ingroup basic_classes
220 /// \class JetDefinition
221 /// class that is intended to hold a full definition of the jet
222 /// clusterer
224 
225 public:
226 
227  /// forward declaration of a class that allows the user to introduce
228  /// their own plugin
229  class Plugin;
230 
231  // forward declaration of a class that will provide the
232  // recombination scheme facilities and/or allow a user to
233  // extend these facilities
234  class Recombiner;
235 
236 
237  /// constructor with alternative ordering or arguments -- note that
238  /// we have not provided a default jet finder, to avoid ambiguous
239  /// JetDefinition() constructor.
240  JetDefinition(JetAlgorithm jet_algorithm_in,
241  double R_in,
242  RecombinationScheme recomb_scheme_in = E_scheme,
243  Strategy strategy_in = Best) {
244  *this = JetDefinition(jet_algorithm_in, R_in, strategy_in, recomb_scheme_in, 1);
245  }
246 
247  /// constructor for algorithms that have no free parameters
248  /// (e.g. ee_kt_algorithm)
249  JetDefinition(JetAlgorithm jet_algorithm_in,
250  RecombinationScheme recomb_scheme_in = E_scheme,
251  Strategy strategy_in = Best) {
252  double dummyR = 0.0;
253  *this = JetDefinition(jet_algorithm_in, dummyR, strategy_in, recomb_scheme_in, 0);
254  }
255 
256  /// constructor for algorithms that require R + one extra parameter to be set
257  /// (the gen-kt series for example)
258  JetDefinition(JetAlgorithm jet_algorithm_in,
259  double R_in,
260  double xtra_param_in,
261  RecombinationScheme recomb_scheme_in = E_scheme,
262  Strategy strategy_in = Best) {
263  *this = JetDefinition(jet_algorithm_in, R_in, strategy_in, recomb_scheme_in, 2);
264  set_extra_param(xtra_param_in);
265  }
266 
267 
268  /// constructor in a form that allows the user to provide a pointer
269  /// to an external recombiner class (which must remain valid for the
270  /// life of the JetDefinition object).
271  JetDefinition(JetAlgorithm jet_algorithm_in,
272  double R_in,
273  const Recombiner * recombiner_in,
274  Strategy strategy_in = Best) {
275  *this = JetDefinition(jet_algorithm_in, R_in, external_scheme, strategy_in);
276  _recombiner = recombiner_in;
277  }
278 
279 
280  /// constructor for case with 0 parameters (ee_kt_algorithm) and
281  /// and external recombiner
282  JetDefinition(JetAlgorithm jet_algorithm_in,
283  const Recombiner * recombiner_in,
284  Strategy strategy_in = Best) {
285  *this = JetDefinition(jet_algorithm_in, external_scheme, strategy_in);
286  _recombiner = recombiner_in;
287  }
288 
289  /// constructor allowing the extra parameter to be set and a pointer to
290  /// a recombiner
291  JetDefinition(JetAlgorithm jet_algorithm_in,
292  double R_in,
293  double xtra_param_in,
294  const Recombiner * recombiner_in,
295  Strategy strategy_in = Best) {
296  *this = JetDefinition(jet_algorithm_in, R_in, xtra_param_in, external_scheme, strategy_in);
297  _recombiner = recombiner_in;
298  }
299 
300  /// a default constructor which creates a jet definition that is in
301  /// a well-defined internal state, but not actually usable for jet
302  /// clustering.
305  }
306 
307 
308  // /// a default constructor
309  // JetDefinition() {
310  // *this = JetDefinition(kt_algorithm, 1.0);
311  // }
312 
313  /// constructor based on a pointer to a user's plugin; the object
314  /// pointed to must remain valid for the whole duration of existence
315  /// of the JetDefinition and any related ClusterSequences
316  JetDefinition(const Plugin * plugin_in) {
317  _plugin = plugin_in;
318  _strategy = plugin_strategy;
319  _Rparam = _plugin->R();
320  _jet_algorithm = plugin_algorithm;
321  set_recombination_scheme(E_scheme);
322  }
323 
324 
325  /// constructor to fully specify a jet-definition (together with
326  /// information about how algorithically to run it).
327  ///
328  /// the ordering of arguments here is old and deprecated (except
329  /// as the common constructor for internal use)
330  JetDefinition(JetAlgorithm jet_algorithm_in,
331  double R_in,
332  Strategy strategy_in,
333  RecombinationScheme recomb_scheme_in = E_scheme,
334  int nparameters_in = 1);
335 
336  /// cluster the supplied particles and returns a vector of resulting
337  /// jets, sorted by pt (or energy in the case of spherical,
338  /// i.e. e+e-, algorithms). This routine currently only makes
339  /// sense for "inclusive" type algorithms.
340  template <class L>
341  std::vector<PseudoJet> operator()(const std::vector<L> & particles) const;
342 
343  /// R values larger than max_allowable_R are not allowed.
344  ///
345  /// We use a value of 1000, substantially smaller than
346  /// numeric_limits<double>::max(), to leave room for the convention
347  /// within PseudoJet of setting unphysical (infinite) rapidities to
348  /// +-(MaxRap + abs(pz())), where MaxRap is 10^5.
349  static const double max_allowable_R; //= 1000.0;
350 
351  /// set the recombination scheme to the one provided
352  void set_recombination_scheme(RecombinationScheme);
353 
354  /// set the recombiner class to the one provided
355  ///
356  /// Note that in order to associate to a jet definition a recombiner
357  /// from another jet definition, it is strongly recommended to use
358  /// the set_recombiner(const JetDefinition &) method below. The
359  /// latter correctly handles the situations where the jet definition
360  /// owns the recombiner (i.e. where delete_recombiner_when_unused
361  /// has been called). In such cases, using set_recombiner(const
362  /// Recombiner *) may lead to memory corruption.
363  void set_recombiner(const Recombiner * recomb) {
364  if (_shared_recombiner()) _shared_recombiner.reset(recomb);
365  _recombiner = recomb;
366  _default_recombiner = DefaultRecombiner(external_scheme);
367  }
368 
369  /// set the recombiner to be the same as the one of 'other_jet_def'
370  ///
371  /// Note that this is the recommended method to associate to a jet
372  /// definition the recombiner from another jet definition. Compared
373  /// to the set_recombiner(const Recombiner *) above, it correctly
374  /// handles the case where the jet definition owns the recombiner
375  /// (i.e. where delete_recombiner_when_unused has been called)
376  void set_recombiner(const JetDefinition &other_jet_def);
377 
378  /// calling this tells the JetDefinition to handle the deletion of
379  /// the recombiner when it is no longer used. (Should not be called
380  /// if the recombiner was initialised from a JetDef whose recombiner
381  /// was already scheduled to delete itself - memory handling will
382  /// already be automatic across both JetDef's in that case).
383  void delete_recombiner_when_unused();
384 
385  /// return a pointer to the plugin
386  const Plugin * plugin() const {return _plugin;};
387 
388  /// calling this causes the JetDefinition to handle the deletion of the
389  /// plugin when it is no longer used
390  void delete_plugin_when_unused();
391 
392  /// return information about the definition...
393  JetAlgorithm jet_algorithm () const {return _jet_algorithm ;}
394  /// same as above for backward compatibility
395  JetAlgorithm jet_finder () const {return _jet_algorithm ;}
396  double R () const {return _Rparam ;}
397  // a general purpose extra parameter, whose meaning depends on
398  // the algorithm, and may often be unused.
399  double extra_param () const {return _extra_param ;}
400  Strategy strategy () const {return _strategy ;}
401  RecombinationScheme recombination_scheme() const {
402  return _default_recombiner.scheme();}
403 
404  /// (re)set the jet finder
405  void set_jet_algorithm(JetAlgorithm njf) {_jet_algorithm = njf;}
406  /// same as above for backward compatibility
407  void set_jet_finder(JetAlgorithm njf) {_jet_algorithm = njf;}
408  /// (re)set the general purpose extra parameter
409  void set_extra_param(double xtra_param) {_extra_param = xtra_param;}
410 
411  /// returns a pointer to the currently defined recombiner.
412  ///
413  /// Warning: the pointer may be to an internal recombiner (for
414  /// default recombination schemes), in which case if the
415  /// JetDefinition becomes invalid (e.g. is deleted), the pointer
416  /// will then point to an object that no longer exists.
417  ///
418  /// Note also that if you copy a JetDefinition with a default
419  /// recombination scheme, then the two copies will have distinct
420  /// recombiners, and return different recombiner() pointers.
421  const Recombiner * recombiner() const {
422  return _recombiner == 0 ? & _default_recombiner : _recombiner;}
423 
424  /// returns true if the current jet definitions shares the same
425  /// recombiner as the one passed as an argument
426  bool has_same_recombiner(const JetDefinition &other_jd) const;
427 
428  /// returns true if the jet definition involves an algorithm
429  /// intended for use on a spherical geometry (e.g. e+e- algorithms,
430  /// as opposed to most pp algorithms, which use a cylindrical,
431  /// rapidity-phi geometry).
432  bool is_spherical() const;
433 
434  /// return a textual description of the current jet definition
435  std::string description() const;
436 
437  /// returns a description not including the recombiner information
438  std::string description_no_recombiner() const;
439 
440  /// a short textual description of the algorithm jet_alg
441  static std::string algorithm_description(const JetAlgorithm jet_alg);
442 
443  /// the number of parameters associated to a given jet algorithm
444  static unsigned int n_parameters_for_algorithm(const JetAlgorithm jet_alg);
445 
446 public:
447  //======================================================================
448  /// @ingroup advanced_usage
449  /// \class Recombiner
450  /// An abstract base class that will provide the recombination scheme
451  /// facilities and/or allow a user to extend these facilities
452  class Recombiner {
453  public:
454  /// return a textual description of the recombination scheme
455  /// implemented here
456  virtual std::string description() const = 0;
457 
458  /// recombine pa and pb and put result into pab
459  virtual void recombine(const PseudoJet & pa, const PseudoJet & pb,
460  PseudoJet & pab) const = 0;
461 
462  /// routine called to preprocess each input jet (to make all input
463  /// jets compatible with the scheme requirements (e.g. massless).
464  virtual void preprocess(PseudoJet & ) const {};
465 
466  /// a destructor to be replaced if necessary in derived classes...
467  virtual ~Recombiner() {};
468 
469  /// pa += pb in the given recombination scheme. Not virtual -- the
470  /// user should have no reason to want to redefine this!
471  inline void plus_equal(PseudoJet & pa, const PseudoJet & pb) const {
472  // put result in a temporary location in case the recombiner
473  // does something funny (ours doesn't, but who knows about the
474  // user's)
475  PseudoJet pres;
476  recombine(pa,pb,pres);
477  pa = pres;
478  }
479 
480  };
481 
482 
483  //======================================================================
484  /// @ingroup advanced_usage
485  /// \class DefaultRecombiner
486  /// A class that will provide the recombination scheme facilities and/or
487  /// allow a user to extend these facilities
488  ///
489  /// This class is derived from the (abstract) class Recombiner. It
490  /// simply "sums" PseudoJets using a specified recombination scheme
491  /// (E-scheme by default)
492  class DefaultRecombiner : public Recombiner {
493  public:
495  _recomb_scheme(recomb_scheme) {}
496 
497  virtual std::string description() const;
498 
499  /// recombine pa and pb and put result into pab
500  virtual void recombine(const PseudoJet & pa, const PseudoJet & pb,
501  PseudoJet & pab) const;
502 
503  virtual void preprocess(PseudoJet & p) const;
504 
505  /// return the index of the recombination scheme
506  RecombinationScheme scheme() const {return _recomb_scheme;}
507 
508  private:
509  RecombinationScheme _recomb_scheme;
510  };
511 
512 
513  //======================================================================
514  /// @ingroup advanced_usage
515  /// \class Plugin
516  /// a class that allows a user to introduce their own "plugin" jet
517  /// finder
518  ///
519  /// Note that all the plugins provided with FastJet are derived from
520  /// this class
521  class Plugin{
522  public:
523  /// return a textual description of the jet-definition implemented
524  /// in this plugin
525  virtual std::string description() const = 0;
526 
527  /// given a ClusterSequence that has been filled up with initial
528  /// particles, the following function should fill up the rest of the
529  /// ClusterSequence, using the following member functions of
530  /// ClusterSequence:
531  /// - plugin_do_ij_recombination(...)
532  /// - plugin_do_iB_recombination(...)
533  virtual void run_clustering(ClusterSequence &) const = 0;
534 
535  virtual double R() const = 0;
536 
537  /// return true if there is specific support for the measurement
538  /// of passive areas, in the sense that areas determined from all
539  /// particles below the ghost separation scale will be a passive
540  /// area. [If you don't understand this, ignore it!]
541  virtual bool supports_ghosted_passive_areas() const {return false;}
542 
543  /// set the ghost separation scale for passive area determinations
544  /// in future runs (strictly speaking that makes the routine
545  /// a non const, so related internal info must be stored as a mutable)
546  virtual void set_ghost_separation_scale(double scale) const;
547  virtual double ghost_separation_scale() const {return 0.0;}
548 
549  /// if this returns false then a warning will be given
550  /// whenever the user requests "exclusive" jets from the
551  /// cluster sequence
552  virtual bool exclusive_sequence_meaningful() const {return false;}
553 
554  /// returns true if the plugin implements an algorithm intended
555  /// for use on a spherical geometry (e.g. e+e- algorithms, as
556  /// opposed to most pp algorithms, which use a cylindrical,
557  /// rapidity-phi geometry).
558  virtual bool is_spherical() const {return false;}
559 
560  /// a destructor to be replaced if necessary in derived classes...
561  virtual ~Plugin() {};
562  };
563 
564 private:
565 
566 
567  JetAlgorithm _jet_algorithm;
568  double _Rparam;
569  double _extra_param ; ///< parameter whose meaning varies according to context
570  Strategy _strategy ;
571 
572  const Plugin * _plugin;
573  SharedPtr<const Plugin> _plugin_shared;
574 
575  // when we use our own recombiner it's useful to point to it here
576  // so that we don't have to worry about deleting it etc...
577  DefaultRecombiner _default_recombiner;
578  const Recombiner * _recombiner;
579  SharedPtr<const Recombiner> _shared_recombiner;
580 
581 };
582 
583 
584 //-------------------------------------------------------------------------------
585 // helper functions to build a jet made of pieces
586 //
587 // These functions include an options recombiner used to compute the
588 // total composite jet momentum
589 // -------------------------------------------------------------------------------
590 
591 /// build a "CompositeJet" from the vector of its pieces
592 ///
593 /// In this case, E-scheme recombination is assumed to compute the
594 /// total momentum
595 PseudoJet join(const std::vector<PseudoJet> & pieces, const JetDefinition::Recombiner & recombiner);
596 
597 /// build a MergedJet from a single PseudoJet
598 PseudoJet join(const PseudoJet & j1,
599  const JetDefinition::Recombiner & recombiner);
600 
601 /// build a MergedJet from 2 PseudoJet
602 PseudoJet join(const PseudoJet & j1, const PseudoJet & j2,
603  const JetDefinition::Recombiner & recombiner);
604 
605 /// build a MergedJet from 3 PseudoJet
606 PseudoJet join(const PseudoJet & j1, const PseudoJet & j2, const PseudoJet & j3,
607  const JetDefinition::Recombiner & recombiner);
608 
609 /// build a MergedJet from 4 PseudoJet
610 PseudoJet join(const PseudoJet & j1, const PseudoJet & j2, const PseudoJet & j3, const PseudoJet & j4,
611  const JetDefinition::Recombiner & recombiner);
612 
613 
614 FASTJET_END_NAMESPACE
615 
616 // include ClusterSequence which includes the implementation of the
617 // templated JetDefinition::operator()(...) member
618 #include "fastjet/ClusterSequence.hh"
619 
620 
621 #endif // __FASTJET_JETDEFINITION_HH__