#include "QFramework/TQCutflowAnalysisJob.h"
#include "QFramework/TQCompiledCut.h"
#include "QFramework/TQAnalysisJob.h"
#include "QFramework/TQCounter.h"
#include "QFramework/TQSample.h"

// #define _DEBUG_
#include "QFramework/TQLibrary.h"

#include <iostream>
#include <fstream>
#include <sstream>
#include <cstdlib>

#include <stdexcept>

////////////////////////////////////////////////////////////////////////////////////////////////
//
// TQCutflowAnalysisJob:
//
// This analysis job allows to book TQCounters at cuts. It works
// similar to the TQHistoMakerAnalysisJob, but as TQCounters don't
// need any configuration options, no configuration strings are
// required.
//
////////////////////////////////////////////////////////////////////////////////////////////////


ClassImp(TQCutflowAnalysisJob)


//______________________________________________________________________________________________

TQCutflowAnalysisJob::TQCutflowAnalysisJob() : 
TQAnalysisJob("TQCutflowAnalysisJob")
{
	// default constructor
}


//______________________________________________________________________________________________

TQCutflowAnalysisJob::TQCutflowAnalysisJob(const TString& name_) : 
  TQAnalysisJob(name_)
{
	// constructor with name
}


//______________________________________________________________________________________________

bool TQCutflowAnalysisJob::initializeSelf() {
  // initialize this analysis job 
  DEBUGclass("initializing analysis job '%s'",this->GetName());

  // we need a parent cut defining the name of the counter 
  if (!this->getCut()) {
    throw std::runtime_error("this analysis job has no cut assigned");
  }

  if ( !this->fCounter ) {
    this->poolAt = this->fSample;
    
    // create a new counter 
    TQCut* c = this->getCut();
    fCounter = new TQCounter(c->GetName(),c->GetTitle());
  }
  DEBUGclass("finished initializing cutflow analysis job");
  return true;
}


//______________________________________________________________________________________________

bool TQCutflowAnalysisJob::finalizeSelf() {
  // get the cutflow folder 
  DEBUGclass("attempting to create .cutflow folder in sample '%s'",this->fSample->getPath().Data());
	
	if(this->poolAt == this->fSample)
		if(!this->finalizeCounter())
			return false;
	
  /* finalize this analysis job */
  return true;

}


//__________________________________________________________________________________|___________

bool TQCutflowAnalysisJob::initializeSampleFolder(TQSampleFolder* sf){
  // initialize this job on a sample folder (taking care of pooling)
  bool pool = false;
  sf->getTagBool(".aj.pool.counters",pool);
  // std::cout << std::endl << "initialize samplefolder called on " << sf->GetName() << " pool=" << pool << ", fHistograms=" << fHistograms << std::endl << std::endl;
  if(pool && !this->fCounter){
    /* create a new counter */
    TQCut* c = this->getCut();
    fCounter = new TQCounter(c->GetName(),c->GetTitle());
    this->poolAt = sf;
  }

  return true;
}

//______________________________________________________________________________________________

bool TQCutflowAnalysisJob::execute(double weight) {
	// count this event: add its weight to the counter 
  fCounter->add(weight*fSample->getNormalisation());

  return true;

}

//______________________________________________________________________________________________

bool TQCutflowAnalysisJob::finalizeCounter(){
	// finalize the counter
	TQFolder * cfFolder = this->poolAt->getFolder(".cutflow+");
	
	// stop if we failed to get the folder 
	if (!cfFolder) { return false; }

	TObject* c = cfFolder->FindObject(fCounter->GetName());
	if(c) cfFolder->Remove(c);

	// add the counter 
	cfFolder->addObject(fCounter);
  
	// remove the pointer to the counter 
	this->fCounter = 0;
	this->poolAt = NULL;
	return true;
}


//__________________________________________________________________________________|___________

bool TQCutflowAnalysisJob::finalizeSampleFolder(TQSampleFolder* sf){
	// finalize the sample folder
  if (!sf) { return false; }
  // finalize this job on a sample folder (taking care of pooling)
	if(sf == this->poolAt)
		return this->finalizeCounter();
	
  return true;
}

//______________________________________________________________________________________________

TQCutflowAnalysisJob::~TQCutflowAnalysisJob() {
	// default destructor
  if (fCounter) { delete fCounter; }
}


 TQCutflowAnalysisJob.cxx:1
 TQCutflowAnalysisJob.cxx:2
 TQCutflowAnalysisJob.cxx:3
 TQCutflowAnalysisJob.cxx:4
 TQCutflowAnalysisJob.cxx:5
 TQCutflowAnalysisJob.cxx:6
 TQCutflowAnalysisJob.cxx:7
 TQCutflowAnalysisJob.cxx:8
 TQCutflowAnalysisJob.cxx:9
 TQCutflowAnalysisJob.cxx:10
 TQCutflowAnalysisJob.cxx:11
 TQCutflowAnalysisJob.cxx:12
 TQCutflowAnalysisJob.cxx:13
 TQCutflowAnalysisJob.cxx:14
 TQCutflowAnalysisJob.cxx:15
 TQCutflowAnalysisJob.cxx:16
 TQCutflowAnalysisJob.cxx:17
 TQCutflowAnalysisJob.cxx:18
 TQCutflowAnalysisJob.cxx:19
 TQCutflowAnalysisJob.cxx:20
 TQCutflowAnalysisJob.cxx:21
 TQCutflowAnalysisJob.cxx:22
 TQCutflowAnalysisJob.cxx:23
 TQCutflowAnalysisJob.cxx:24
 TQCutflowAnalysisJob.cxx:25
 TQCutflowAnalysisJob.cxx:26
 TQCutflowAnalysisJob.cxx:27
 TQCutflowAnalysisJob.cxx:28
 TQCutflowAnalysisJob.cxx:29
 TQCutflowAnalysisJob.cxx:30
 TQCutflowAnalysisJob.cxx:31
 TQCutflowAnalysisJob.cxx:32
 TQCutflowAnalysisJob.cxx:33
 TQCutflowAnalysisJob.cxx:34
 TQCutflowAnalysisJob.cxx:35
 TQCutflowAnalysisJob.cxx:36
 TQCutflowAnalysisJob.cxx:37
 TQCutflowAnalysisJob.cxx:38
 TQCutflowAnalysisJob.cxx:39
 TQCutflowAnalysisJob.cxx:40
 TQCutflowAnalysisJob.cxx:41
 TQCutflowAnalysisJob.cxx:42
 TQCutflowAnalysisJob.cxx:43
 TQCutflowAnalysisJob.cxx:44
 TQCutflowAnalysisJob.cxx:45
 TQCutflowAnalysisJob.cxx:46
 TQCutflowAnalysisJob.cxx:47
 TQCutflowAnalysisJob.cxx:48
 TQCutflowAnalysisJob.cxx:49
 TQCutflowAnalysisJob.cxx:50
 TQCutflowAnalysisJob.cxx:51
 TQCutflowAnalysisJob.cxx:52
 TQCutflowAnalysisJob.cxx:53
 TQCutflowAnalysisJob.cxx:54
 TQCutflowAnalysisJob.cxx:55
 TQCutflowAnalysisJob.cxx:56
 TQCutflowAnalysisJob.cxx:57
 TQCutflowAnalysisJob.cxx:58
 TQCutflowAnalysisJob.cxx:59
 TQCutflowAnalysisJob.cxx:60
 TQCutflowAnalysisJob.cxx:61
 TQCutflowAnalysisJob.cxx:62
 TQCutflowAnalysisJob.cxx:63
 TQCutflowAnalysisJob.cxx:64
 TQCutflowAnalysisJob.cxx:65
 TQCutflowAnalysisJob.cxx:66
 TQCutflowAnalysisJob.cxx:67
 TQCutflowAnalysisJob.cxx:68
 TQCutflowAnalysisJob.cxx:69
 TQCutflowAnalysisJob.cxx:70
 TQCutflowAnalysisJob.cxx:71
 TQCutflowAnalysisJob.cxx:72
 TQCutflowAnalysisJob.cxx:73
 TQCutflowAnalysisJob.cxx:74
 TQCutflowAnalysisJob.cxx:75
 TQCutflowAnalysisJob.cxx:76
 TQCutflowAnalysisJob.cxx:77
 TQCutflowAnalysisJob.cxx:78
 TQCutflowAnalysisJob.cxx:79
 TQCutflowAnalysisJob.cxx:80
 TQCutflowAnalysisJob.cxx:81
 TQCutflowAnalysisJob.cxx:82
 TQCutflowAnalysisJob.cxx:83
 TQCutflowAnalysisJob.cxx:84
 TQCutflowAnalysisJob.cxx:85
 TQCutflowAnalysisJob.cxx:86
 TQCutflowAnalysisJob.cxx:87
 TQCutflowAnalysisJob.cxx:88
 TQCutflowAnalysisJob.cxx:89
 TQCutflowAnalysisJob.cxx:90
 TQCutflowAnalysisJob.cxx:91
 TQCutflowAnalysisJob.cxx:92
 TQCutflowAnalysisJob.cxx:93
 TQCutflowAnalysisJob.cxx:94
 TQCutflowAnalysisJob.cxx:95
 TQCutflowAnalysisJob.cxx:96
 TQCutflowAnalysisJob.cxx:97
 TQCutflowAnalysisJob.cxx:98
 TQCutflowAnalysisJob.cxx:99
 TQCutflowAnalysisJob.cxx:100
 TQCutflowAnalysisJob.cxx:101
 TQCutflowAnalysisJob.cxx:102
 TQCutflowAnalysisJob.cxx:103
 TQCutflowAnalysisJob.cxx:104
 TQCutflowAnalysisJob.cxx:105
 TQCutflowAnalysisJob.cxx:106
 TQCutflowAnalysisJob.cxx:107
 TQCutflowAnalysisJob.cxx:108
 TQCutflowAnalysisJob.cxx:109
 TQCutflowAnalysisJob.cxx:110
 TQCutflowAnalysisJob.cxx:111
 TQCutflowAnalysisJob.cxx:112
 TQCutflowAnalysisJob.cxx:113
 TQCutflowAnalysisJob.cxx:114
 TQCutflowAnalysisJob.cxx:115
 TQCutflowAnalysisJob.cxx:116
 TQCutflowAnalysisJob.cxx:117
 TQCutflowAnalysisJob.cxx:118
 TQCutflowAnalysisJob.cxx:119
 TQCutflowAnalysisJob.cxx:120
 TQCutflowAnalysisJob.cxx:121
 TQCutflowAnalysisJob.cxx:122
 TQCutflowAnalysisJob.cxx:123
 TQCutflowAnalysisJob.cxx:124
 TQCutflowAnalysisJob.cxx:125
 TQCutflowAnalysisJob.cxx:126
 TQCutflowAnalysisJob.cxx:127
 TQCutflowAnalysisJob.cxx:128
 TQCutflowAnalysisJob.cxx:129
 TQCutflowAnalysisJob.cxx:130
 TQCutflowAnalysisJob.cxx:131
 TQCutflowAnalysisJob.cxx:132
 TQCutflowAnalysisJob.cxx:133
 TQCutflowAnalysisJob.cxx:134
 TQCutflowAnalysisJob.cxx:135
 TQCutflowAnalysisJob.cxx:136
 TQCutflowAnalysisJob.cxx:137
 TQCutflowAnalysisJob.cxx:138
 TQCutflowAnalysisJob.cxx:139
 TQCutflowAnalysisJob.cxx:140
 TQCutflowAnalysisJob.cxx:141
 TQCutflowAnalysisJob.cxx:142
 TQCutflowAnalysisJob.cxx:143
 TQCutflowAnalysisJob.cxx:144
 TQCutflowAnalysisJob.cxx:145
 TQCutflowAnalysisJob.cxx:146
 TQCutflowAnalysisJob.cxx:147
 TQCutflowAnalysisJob.cxx:148
 TQCutflowAnalysisJob.cxx:149
 TQCutflowAnalysisJob.cxx:150
 TQCutflowAnalysisJob.cxx:151
 TQCutflowAnalysisJob.cxx:152
 TQCutflowAnalysisJob.cxx:153
 TQCutflowAnalysisJob.cxx:154
 TQCutflowAnalysisJob.cxx:155
 TQCutflowAnalysisJob.cxx:156
 TQCutflowAnalysisJob.cxx:157