/** 
* @file DTBRandom.h
* @brief random decision tree
* @author Erik Rodner
* @date 05/06/2008

*/
#ifndef DTBRANDOMINCLUDE
#define DTBRANDOMINCLUDE

#include "core/vector/VectorT.h"
#include "core/vector/MatrixT.h"

#include "core/basics/Config.h"
#include "DecisionTreeBuilder.h"
#include "vislearning/cbaselib/CachedExample.h"


namespace OBJREC {

/** random decision tree */
class DTBRandom : public DecisionTreeBuilder
{
    protected:
	int random_split_tests;
	int random_features;
	int max_depth;
	int min_examples;
	double minimum_information_gain;
	double minimum_entropy;

	bool use_shannon_entropy;
	int random_split_mode;

	/** saves indices in leaves */
	bool save_indices;
	enum {
	    RANDOM_SPLIT_INDEX = 0,
	    RANDOM_SPLIT_UNIFORM
	};

    
	DecisionNode *buildRecursive ( const FeaturePool & fp, 
		     const Examples & examples,
		     std::vector<int> & examples_selection,
		     FullVector & distribution,
		     double entropy,
		     int maxClassNo,
		     int depth );

#if 0
	double entropy ( const FeatureValues & values,
		     const FeatureValues::const_iterator & begin,
		     const FeatureValues::const_iterator & end,
		     std::vector<int> & examples,
		     FullVector & stat );
#endif

	bool entropyLeftRight ( const FeatureValuesUnsorted & values,
		     double threshold,
		     double* stat_left,
		     double* stat_right,
		     double & entropy_left,
		     double & entropy_right,
		     double & count_left,
		     double & count_right,
		     int maxClassNo );

    public:
  
	/** simple constructor */
	// refactor-nice.pl: check this substitution
	// old: DTBRandom( const NICE::Config *conf, string section = "DTBRandom" );
	DTBRandom( const NICE::Config *conf, std::string section = "DTBRandom" );
      
	/** simple destructor */
	virtual ~DTBRandom();
 
	DecisionNode *build ( const FeaturePool & fp, 
		     const Examples & examples,
		     int maxClassNo );
    
};


} // namespace

#endif
