1 #ifndef __FASTJET_NNH_HH__ 
    2 #define __FASTJET_NNH_HH__ 
   34 #include "fastjet/NNBase.hh" 
   36 FASTJET_BEGIN_NAMESPACE      
 
   75 template<
class BJ, 
class I = _NoInfo> 
class NNH : 
public NNBase<I> {
 
   80   NNH(
const std::vector<PseudoJet> & jets)           : 
NNBase<I>()     {start(jets);}
 
   81   NNH(
const std::vector<PseudoJet> & jets, I * info) : 
NNBase<I>(info) {start(jets);}
 
   84   void start(
const std::vector<PseudoJet> & jets);
 
   88   double dij_min(
int & iA, 
int & iB);
 
   91   void remove_jet(
int iA);
 
   95   void merge_jets(
int iA, 
int iB, 
const PseudoJet & jet, 
int jet_index);
 
  108   void set_NN_crosscheck(NNBJ * jet, NNBJ * begin, NNBJ * end);
 
  112   void set_NN_nocross   (NNBJ * jet, NNBJ * begin, NNBJ * end);
 
  124   std::vector<NNBJ *> where_is;
 
  128   class NNBJ : 
public BJ {
 
  130     void init(
const PseudoJet & jet, 
int index_in) {
 
  132       other_init(index_in);
 
  134     void init(
const PseudoJet & jet, 
int index_in, I * info) {
 
  136       other_init(index_in);
 
  138     void other_init(
int index_in) {
 
  140       NN_dist = BJ::beam_distance();
 
  143     int index()
 const {
return _index;}
 
  159   briefjets = 
new NNBJ[n];
 
  160   where_is.resize(2*n);
 
  162   NNBJ * jetA = briefjets;
 
  165   for (
int i = 0; i< n; i++) {
 
  167     this->init_jet(jetA, jets[i], i);
 
  176   for (jetA = head + 1; jetA != tail; jetA++) {
 
  180     set_NN_crosscheck(jetA, head, jetA);
 
  189   double diJ_min = briefjets[0].NN_dist;
 
  191   for (
int i = 1; i < n; i++) {
 
  192     if (briefjets[i].NN_dist < diJ_min) {
 
  194       diJ_min  = briefjets[i].NN_dist;
 
  199   NNBJ * jetA = & briefjets[diJ_min_jet];
 
  202   iB = jetA->NN ? jetA->NN->index() : -1;
 
  210   NNBJ * jetA = where_is[iA];
 
  217   where_is[jetA->index()] = jetA;
 
  219   for (NNBJ * jetI = head; jetI != tail; jetI++) {
 
  221     if (jetI->NN == jetA) set_NN_nocross(jetI, head, tail);
 
  224     if (jetI->NN == tail) {jetI->NN = jetA;}
 
  233   NNBJ * jetA = where_is[iA];
 
  234   NNBJ * jetB = where_is[iB];
 
  240   if (jetA < jetB) std::swap(jetA,jetB);
 
  244   this->init_jet(jetB, jet, index);
 
  246   if (index >= 
int(where_is.size())) where_is.resize(2*index);
 
  247   where_is[jetB->index()] = jetB;
 
  255   where_is[jetA->index()] = jetA;
 
  257   for (NNBJ * jetI = head; jetI != tail; jetI++) {
 
  259     if (jetI->NN == jetA || jetI->NN == jetB) {
 
  260       set_NN_nocross(jetI, head, tail);
 
  265     double dist = jetI->distance(jetB);
 
  266     if (dist < jetI->NN_dist) {
 
  268         jetI->NN_dist = dist;
 
  272     if (dist < jetB->NN_dist) {
 
  274         jetB->NN_dist = dist;
 
  280     if (jetI->NN == tail) {jetI->NN = jetA;}
 
  288                     NNBJ * begin, NNBJ * end) {
 
  289   double NN_dist = jet->beam_distance();
 
  291   for (NNBJ * jetB = begin; jetB != end; jetB++) {
 
  292     double dist = jet->distance(jetB);
 
  293     if (dist < NN_dist) {
 
  297     if (dist < jetB->NN_dist) {
 
  298       jetB->NN_dist = dist;
 
  303   jet->NN_dist = NN_dist;
 
  310 template <
class BJ, 
class I>  
void NNH<BJ,I>::set_NN_nocross(
 
  311                  NNBJ * jet, NNBJ * begin, NNBJ * end) {
 
  312   double NN_dist = jet->beam_distance();
 
  317     for (NNBJ * jetB = begin; jetB != jet; jetB++) {
 
  318       double dist = jet->distance(jetB);
 
  319       if (dist < NN_dist) {
 
  328     for (NNBJ * jetB = jet+1; jetB != end; jetB++) {
 
  329       double dist = jet->distance (jetB);
 
  330       if (dist < NN_dist) {
 
  337   jet->NN_dist = NN_dist;
 
  343 FASTJET_END_NAMESPACE      
 
  346 #endif // __FASTJET_NNH_HH__