/**
 * @class cUnivers
 * file name: cUnivers.cpp
 * @author Betti Oesterholz
 * @date 12.01.2005
 * @mail webmaster@bernd-oesterholz.name
 *
 * System: C++
 *
 * This class represents a basic univers.
 * Copyright (C) @c GPL3 2008  Betti Oesterholz
 *
 * This program is free software: you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation, either version 3 of the License, or
 * any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program. If not, see <http://www.gnu.org/licenses/>.
 *
 *
 * This file contains the program for a univers.
 * Ther are 2 basictypes in this univers points and conections(positiv and
 * negativ) betwean them. Points are changing Points of the univers.
 * Every tick(minimum time) every point creates a new zero distance. (nothing is
 * produced, conservation of distances) A zero distance is a positiv (+1) and a
 * negativ (-1) distance. The 2 signed distances are random conected to a
 * neigbor of the point or a new point. (each possibility has same probability)
 * Neigbor points of a point are points that are conected with distances to the point.
 * Two not eqaul signed distances betwean to points destroy each other.(add to zero)
 * If one part (signed distance) of a zero distanc is destroyed, but not the
 * other, the other distance one end ist displaced from the point of his
 * creation to the point that was conected with the creation point by the
 * destroyed distance. (the distance betwean the end and the point becomes zero)
 * 
 * translation diagram:(for tree points)
 * 	- pi point i=1..3
 * 	- + positiv distance
 * 	- - negativ distance
 * 	- no distance
 * 	- befor -> after
 * 	- p2 is the point wher the zero distance is created, p1 is the point choosen
 * 	- for the positiv part(distance) to go to and p3 is the point choosen
 * 	- for the negativ part(distance) to go to 
 * 
 * 	- 1) p1+p2+p3 -> p3+p1+p2
 * 	- 2) p1+p2-p3 -> p1++p2--p3
 * 	- 3) p1-p2+p3 -> p1 p2 p3
 * 	- 4) p1-p2-p3 -> p3-p1-p2
 * 	- 5) p1+p2 p3 -> p1++p2-p3
 * 	- 6) p1 p2+p3 -> p1+p3 p2
 * 	- 7) p1-p2 p3 -> p1-p3 p2
 * 	- 8) p1 p2-p3 -> p1+p2--p3
 * 	- 9) p1 p2 p3 -> p1+p2-p3
 */
/*
History:
18.10.2008  Oesterholz  parameters for new function for outputting the statistic for the univers parts
*/

#ifndef ___UNIVERS_h__
#define ___UNIVERS_h__

#include <iostream>
//#include <stdio.h>
#include <fstream>
#include <list>
#include <utility>
//#include <ctime>// define time()

#include "cRandomMersenne.h"
#include "nReadValues.h"
#include "cPoint.h"

#define UNIVERS_VERSION "V2.0"

using std::list;
using std::pair;
using std::ostream;
using std::ofstream;
using std::fstream;
using std::ios;
using std::istream;
using std::ifstream;
using std::cout;
using std::endl;
using std::flush;
using namespace nReadValues;

/** @class TOPoint output form of a cPoint */
class TOPoint{
public:
	/** pointer to the original point */
	cPoint* original;
	/** positiv neibors */
	list<unsigned long> pPoint;
	/** negativ neibors */
	list<unsigned long> nPoint;
};


/** @class TUPart part universes, with relevant data */
class TUPart{
public:
	/** the part univers structur */
	list<cPoint*> partUnivers;
	/** positiv Distances */
	unsigned long pDistances;
	/** negativ Distance */
	unsigned long nDistances;
	/** last given name */
	unsigned long last;
	
	bool operator<(const TUPart part) const{
		return ((pDistances+nDistances)<(part.pDistances+part.nDistances));
	}

	bool operator>(const TUPart part) const{
		return ((pDistances+nDistances)>(part.pDistances+part.nDistances));
	}
};

/** @class cParameter to store the line and comments of the parameter */
class cParameter{
public:
	/** line wher the parameter should be writen */
	unsigned int line;
	/** number of the parameter */
	unsigned int number;
	/** description of the parameter */
	char* name;

	/**
	 * standart constructor of this class;
	 * standart values are 0 far all
	 */
	cParameter():line(0),number(0),name(0){
	}

	/**
	 * copy constructor of this class;
	 * copies the values and the name string
	 */
	cParameter(const cParameter &tPara):line(tPara.line),number(tPara.number){
		if(tPara.name){
			unsigned int i=0;
			for(i=0;tPara.name[i]!=0;i++){}//cont chars of the name of tPara
			name=new char[i+1];
			for(unsigned int a=0;a<=i;a++){name[a]=tPara.name[a];}
		}else{
			name=NULL;
		}
	}
	
	/**
	 * standart constructor of this class;
	 * standart values are 0 far all
	 */
	~cParameter(){
		if (name)
			{delete name;}
	}

	/**
	 * order the parameter by lines
	 * @param para a paramerter para to compare this parameter with
	 * @return true if this parameter has a lower line as te given parameter, else false
	 */
	bool operator<(const cParameter para) const{
		return (line<(para.line));
	}

};

/** @class cUnivers implements the univers and functions for analysing it */
class cUnivers
{

protected:
	/** random number generator */
	cRandomMersenne *rg1;
	
	/** structur of the univers */
	list<cPoint*> univers;
	/** intern time(number of ticks till creation) */
	unsigned long iTime;
	/** number of positiv distances */
	unsigned long pDistance;
	/** number of negativ distances */
	unsigned long nDistance;
	/** number of transitions for the different transitions 
	 * , index 0 is the sum of all transitions (see this file begin for 
	 * description of the other transition numbers)
	 */
	unsigned long trans[10];
	/** number/name of the last created point */
	unsigned long last; 
	
	/** output comments? */
	bool outComent;
	/** cut every cutAfter ticks; if 0 don't cut */
	unsigned long cutAfter;
	/** output the actual univers every outUniv ticks; if 0 don't output */
	unsigned long outUniv;
	/** output the statistics every outStat ticks; if 0 don't output */
	unsigned long outStat;
	
	/** the basis time to begin conting with */
	long bTime;
	/** maximal Time (0 = infinum); if iTime > maxTime stop evaluation(tick) */
	unsigned long maxTime;
	/** maximal number of points after iteration/tick (0 = infinum),
	 * if the univers has more after a tick the end condition is reached
	 */
	unsigned long maxPoints;
	/** check maxPoints condition every checkMaxPoints ticks; 
	 * if 0 don't check; standart is 1 
	 */
	unsigned long checkMaxPoints;
	
	/** name of the statistic file */
	char* statFileName;
	/** statistic file */
	fstream *statFile;
	/** if the statisticfile-parameter are changed till the last init */
	bool bStatParameterChanged;
/** @def STATISTIC_ROWS number of rows in the statistic file */
#define STATISTIC_ROWS 25

	/** folder for the universes to write to, standart is: "./universes/" */
	char* uFolder;
	/** base name for the universes files, standart is: "univers" it will 
	 * be converted to "univers(bTime+iTime).txt */
	char* bUName;
	/** if the universfile- parameter are changed till the last init */
	bool bUniversParameterChanged;
	
	/** the dimension the choosen univers should be nearest to in the cut operation */
	double cutNearDimension;
	/** cut operator the size ratio to the maximal univers, till wich 
	 * universes are put in the class to choose the best from (best is 
	 * the one with a dimension nearest cutNearDimension)
	 */
	double cutMaxClassRatio;
	
	/** is true if the new univers data should appendet to the old */
	bool appendUnivers;
	
	/** the file wher the parameters are loaded from and should be stored 
	 * to if the univers should appended */
	char* parameterFile;
	/** the numbers and text to the parameter of this class instance */
	list<cParameter> parameter;
	
	/**output the real time statistic every outRealTime ticks; if 0 don't check */
	unsigned long outRealTime;
	/** the name of the file wher the real time statistic should be outputed */
	char* rTimeFileName;
	/** the file wher the real time statistic is stored (Null=no file)*/
	fstream *rTimeFile;
	/** if the realtime -parameter have changed till the last init */
	bool bRTimeParameterChanged;
	
	/**output the cut time statistic every outCutStatistic ticks; if 0 don't check */
	unsigned long outCutStatistic;
	/** the name of the file wher the cut statistic should be outputed */
	char* cutFileName;
	/** the file wher the cut statistic is stored (Null=no file)*/
	fstream *cutFile;
	/** if the cutstatistic -parameter have changed till the last init */
	bool bCutParameterChanged;
	
	/**output the univers part time statistic every lOutUniversPartStatistic ticks; if 0 don't check */
	unsigned long lOutUniversPartStatistic;
	/** the name of the file wher the univers part statistic should be outputed */
	char* szUniversPartStatisticFileName;
	/** the file wher the univers part statistic is stored (Null=no file)*/
	fstream *universPartStatisticFile;
	/** if the univers -part -parameter have changed till the last init */
	bool bUniversPartStatisticParameterChanged;
	
	/** number of possible transitions in the univers */
	unsigned long long transPosible;
	/** the actual point of the univers, wher the transition had happened */
	list<cPoint*>::iterator actualPoint;

	/** this variable helps to spead up the algorithm, be carefull if you 
	 * change this, the value of all points tmpValue variables should 
	 * always be smale as this tmpValue of the univers
	 */
	unsigned long tmpValue;
	
	/** flag, if true then the next endCondition call returns true */
	bool bEndEvaluation;
	
	/** sets all tmpValues (of all points and the univers) to 0 */
	void nullTMPValues();
	

	/** init the enviroment of the univers;
	 * crates directoris for statistics und other output;
	 * for failed initialisations the bXXXChanged-Variable is true
	 * @return 0 if all inits are OK; the number of faild initialisations is returned;
	 */
	int initUnivers();

public:
	/**
	 * standart constructor, constructs a new univers with standart values
	 * standart statistic file is: "./statistics.txt"
	 */
	cUnivers();

	/**
	 * parameter constructor, constructs a new univers with standart values
	 * Beware!: this constructor copies just the char* pointers, but not 
	 * 	the string in them!
	 * @param outC output comments
	 * @param cutA cut after steps, standart: 0
	 * @param mTm number of maxTime, standart: 1000
	 * @param maxP maxPoints the univers should have, standart: 0 (=infinity points)
	 * @param cMP check maxPoints condition every  (checkMaxPoints) ticks,
	 *		 standart: 1
	 * @param stat name of the statistic file, standart: "./statistics.txt"
	 * @param uFol folder wher to write the universes to, standart: "./universes/"
	 * @param bUN the filenamestart of the univers files, standart: "univers"
	 * @param cutDim the dimension to prefer by cut (cutNearDimension), 
	 *		standart: 3.0
	 * @param cutRatio the Ratio till wich to generate the max class by cut 
	 *		(cutMaxClassRatio), standart: 1.0
	 * @param appU append univers if appU is true, standart: false
	 */
	cUnivers( bool outC, unsigned int cutA=0, unsigned long mTm=1000, unsigned long maxP=0, 
		unsigned long cMP=1, const char* stat="./statistics.txt", const char* uFol="./universes/", 
		const char* bUN="univers", double cutDim=3.0, double cutRatio=1.0, bool appU=false);

	/** 
	 * copy constructor, constructs a copy of the given univers;
	 * statistic output cycles will be set to 0 and append univers will be false
	 */
	cUnivers(cUnivers &univ);

	/**
	 * destructor
	 * destructs the univers and closes all open files
	 */
	~cUnivers();

	/**
	 * returns a copy of the given univers
	 * @param univ a univers to copy
	 * @return a copy of the given univers
	 */
	list<cPoint*> &copyUniversStructur( list<cPoint*> &univ ) const;

	/** 
	 * returns a pointer to the univers
	 * @return the pointer to the univers structur
	 */
	list<cPoint*>* getUniversStructur();

	/**
	 * returns the univers data;
	 * dosn't copies the univers, you get the data of the original univers 
	 * @return the data of the univers in a TUPart, with the pointer to the univers structur
	 */
	TUPart getUnivers();

	/**
	 * @return the number of the points of the univers
	 */
	unsigned long getNumberOfPoints() const;

	/**
	 * returns the internal time (number of ticks till creation) of the univers
	 * @return the internal time of the univers
	 */
	unsigned long getInternalTime() const;

	/** 
	 * @return the number of the positiv distances of the univers
	 */
	unsigned long getNumberOfPDistance() const;

	/**
	 * @return the number of the negativ Distances of the univers
	 */
	unsigned long getNumberOfNDistance() const;

	/**
	 * returns the number of the different transitions in the last tick(0-9)
	 * like in the transition diagram above; array point 0 is the transition sum
	 * @return the number of differnt transitions of the last tick
	 */
	unsigned long* getNumberOfLastTransitions();

	/**
	 * @return the last name number a new point in the univers was given
	 */
	unsigned long getLastName() const;

	/**
	 * returns if comments are shown
	 * @return true if comments are shown, else false
	 */
	 bool getCommentsActiv() const;

	/**
	 * returns the after wich number of ticks a cut is performed,
	 * if 0 is returned, it wouldn't be cut
	 * @return after wich number of ticks a cut is performed
	 */
	unsigned long getCutCycle() const;

	/**
	 * returns after wich number of ticks a the univers is outputed,
	 * if 0 is returned the univers isn't outputed
	 * @return after wich number of ticks the univers is outputed
	 */
	unsigned long getOutUniversCycle() const;

	/**
	 * returns the after wich number of ticks a the statistics is outputed,
	 * if 0 is returned no statistic will be outputed
	 * @return after wich number of ticks the statistics is outputed
	 */
	unsigned long getOutStatisticCycle() const;

	/**
	 * @return the time base (=beginning time) of the univers (the time the univers begins is user defined)
	 */
	long getTimeBase() const;

	/**
	 * returns the maximal time, at this time the evaluation of the univers 
	 * will be stoped;
	 * if the maximal time is 0 evaluation isn't stop because of the time
	 * @return the maximal time
	 */
	unsigned long getMaxNumberOfTime() const;

	/**
	 * returns how many point the univers can have bevor it's evaluetion is stoped; 
	 * if the number is 0 the univers wouldn't be stoped because it has to much points
	 * @return the maximal number of point
	 */
	unsigned long getMaxNumberOfPoints() const;

	/**
	 * returns every wich number of ticks the max points condition should be
	 * checked; if 0 the condition will be never check
	 * @return the number of ticks the max points condition is checked
	 */
	unsigned long getCheckMaxPoints() const;

	/**
	 * @return the statistic file name
	 */
	char* getStatisticFileName() const;

	/**
	 * @return the univers folder name, wher the actual universes files are writen to
	 */
	char* getUniversFolderName() const;

	/**
	 * @return the univers file base name, with wich the saved universes files begin with
	 */
	char* getUniversFileBaseName() const;


	/**
	 * @return the cutNearDimension value 
	 * (the value the dimension of the remaining part after a cut operation 
	 * should be near to )
	 */
	double getCutNearDimension() const;

	/**
	 * @return the cutMaxClassRatio value
	 */
	double getCutMaxClassRatio() const;

	/**
	 * @return the number of ticks betwean writing the realtime statistic 
	 *   to a file, if the number is 0 no statistic is writen
	 */
	unsigned long getOutRealTime() const;
	
	/**
	 * @return the name of the real time statistic file
	 */
	char* getRTimeFileName() const;

	/**
	 * @return the number of ticks betwean writing the cut statistic 
	 *   to a file, if the number is 0 no statistic is writen
	 */
	unsigned long getOutCutStatistic() const;

	/**
	 * @return the name of the cut statistic file
	 */
	char* getCutFileName() const;
	
	/**
	 * @return in which intervall the univers part statistic should be outputed
	 */
	unsigned long getOutUniversPartStatistic() const {
		return lOutUniversPartStatistic;
	}

	/**
	 * @return the univers part statistic file name
	 */
	char* getUniversPartStatisticFileName() const {
		return szUniversPartStatisticFileName;
	}

//set methods

	/** adds the given number to the number of positiv distances of the univers
	 * if the old number of positiv distances plus the given value is lower 0 the
	 * number of positiv distances is set to 0
	 * @param  pDDist number( positiv or negativ) to add to the positiv distances
	 * @return the changed number of postitiv distances of the univers
	 */
	unsigned long addNumberOfPDistance( const long pDDist );

	/**
	 * adds the given number to the number of negativ distances of the univers;
	 * if the old number of negativ distances plus the given value is lower 0 
	 * the number of negativ distances is set to 0
	 * @param nDDist number(positiv or negativ) to add to the negativ distances
	 * @return the changed negativ distances of the univers
	 */
	unsigned long  addNumberOfNDistance(const long nDDist);

	/**
	 * adds the given number to the number of posible transitions of the univers;
	 * if the old number of transitions posible plus the given value is 
	 * lower 0 the number of transitions posible is set to 0
	 * @param lTransitions number(positiv or negativ) to add to the transitions posible
	 * @return the changed transitions posible of the univers
	 */
	unsigned long addTransPosible( const long lTransitions );

	/**
	 * evalues the posible transitions for this univers;
	 * the transPosible value of this univers is changed
	 * @return the number of posible transitions
	 */
	unsigned long evalueTransPosible();

	/**
	 * set if comments are shown
	 * @param bCommentActive a value if the comments should be shown
	 */
	void setCommentsActiv( const bool bCommentActive );

	/**
	 * set in which interval (every which number of ticks) a cut is 
	 * performed, 0 means never cut
	 * @param ulCutAfter number of ticks betwean the cut operation
	 */
	void setCutCycle( const unsigned long ulCutAfter );

	/**
	 * set in which interval (every which number of ticks) a the statistics 
	 * is generated and writen, 0 means never generate the statistic
	 * @param ulOutStatistic after wich number of ticks the statistics is outputed
	 * @return true if the interval for the statistics is changed to the
	 * 	given value, else false
	 */
	bool setOutStatisticCycle( const unsigned long ulOutStatistic );

	/**
	 * set the time base of the univers (the time the univers begins with
	 * is user defined), the first tick of the univers will be at this time
	 * @param lBaseTime the time base
	 */
	void setTimeBase( const long lBaseTime );

	/**
	 * set the maximal time; 
	 * if this time is reached the evaluation of the univers will stop;
	 * if the maximal time is set to 0 the univers won't stop because of
	 * the time
	 * @param ulMaxTime the maximal time to set
	 */
	void setMaxNumberOfTime( const unsigned long ulMaxTime );

	/**
	 * set maximal number of points (counted after a tick);
	 * if this number is reached the evaluation of the univers will stop;
	 * if the maximal number of points is set to 0 the univers won't stop
	 * because of the number of points
	 * @param ulMaxPoints the maximal number of points to set
	 */
	void setMaxNumberOfPoints( const unsigned long ulMaxPoints );

	/**
	 * set in which interval (every which number of ticks) a the maximal
	 * number of points condition is checked; 
	 * 0 means never checked the condition
	 * @param ulCeckMaxPoints after wich number of ticks the maximal number 
	 *		of points condition
	 */
	void setCheckMaxPoints( const unsigned long ulCeckMaxPoints );

	/**
	 * set statistic file name
	 * @param  pStatFileName a pointer to the statistic file name
	 * @return true if the filename was set, else false
	 */
	bool setStatisticFileName( const char* pStatFileName );

	/**
	 * set in which interval (wich number of ticks) a the univers is outputed;
	 * if the value is 0 the univers isn't outputed in an interval
	 * @see setUniversFolderName
	 * @see setUniversFileBaseName
	 * @param ulOutputUnivers after wich number of ticks the univers is outputed
	 * @return true if the value was changed, else false
	 */
	bool setOutUniversCycle( const unsigned long ulOutputUnivers );

	/**
	 * set the univers folder name, wher the files for the universes are
	 * writen to
	 * @see setOutUniversCycle
	 * @see setUniversFileBaseName
	 * @param pUniversFolder a pointer to the the univers folder
	 * @return true if the value is changed, else false
	 */
	bool setUniversFolderName( const char* pUniversFolder );

	/**
	 * set the univers file base name, with wich the saved universes begin with
	 * @see setOutUniversCycle
	 * @see setUniversFolderName
	 * @param pUniversFileBaseName the univers base name
	 * @return true if the value is changed, else false
	 */
	bool setUniversFileBaseName( const char* pUniversFileBaseName );

	/**
	 * set the cutNearDimension value (the value the dimension of the 
	 * remaining part after a cut operation should be near to )
	 * @see getCutNearDimension
	 * @see setCutMaxClassRatio
	 * @param dCutNearDimension the cutNearDimension value to set
	 */
	void setCutNearDimension( const double dCutNearDimension );

	/**
	 * set the cutMaxClassRatio value; the size, in ratio to the biggest
	 * univers parts, the universparts from which the after the cut
	 * remaining universpart is choosen from
	 * @see getCutMaxClassRatio
	 * @see setCutNearDimension
	 * @param dCutMaxClassRatio the cutMaxClassRatio value to set
	 */
	void setCutMaxClassRatio( const double dCutMaxClassRatio );

	/**
	 * set if the real time statistic should be outputed
	 * @see setRTimeFileName
	 * @param bRealTime the outRealTime value
	 * @return true if the value is changed, else false
	 */
	bool setOutRealTime( bool bRealTime );

	/**
	 * set real time statistic path
	 * @see setOutRealTime
	 * @param pRealTimePath a pointer to the real time statistic file name
	 * @return true if the value is changed, else false
	 */
	bool setRTimeFileName( const char* pRealTimePath );

	/** prints the head of the real time statistic to the real time statistic file */
	void printRealTimeStatisticHead() const;

	/**
	 * set in which interval (every which number of ticks) the cut
	 * statistic should be outputed;
	 * 0 means never output the statistic;
	 * the cut statistic interval should be a multiple of the cut interval,
	 * because if ther is no cut operation no cut statistic can be generated
	 * @see setCutFileName
	 * @see getOutCutStatistic
	 * @param lOutCutStatistic after wich number of ticks the cut statistic 
	 * 	should be outputed
	 */
	bool setOutCutStatistic( const unsigned long lOutCutStatistic );

	/**
	 * set cut statistic path
	 * @see setOutCutStatistic
	 * @see getCutFileName
	 * @param pCutStatisticPath a pointer to the cut statistic file name
	 * @return true if the value is changed, else false
	 */
	bool setCutFileName( const char* pCutStatisticPath );

	/**
	 * set if the univers parts statistic should be outputed
	 * @param universPartStatisticInterval how often the univers part statistic should be outputed (0=never)
	 * @return true if the value is changed, else false
	 */
	bool setOutUniversPartStatistic(const unsigned long universPartStatisticInterval);

	/**
	 * set univers parts statistic file name
	 * @param  universPartFilename a pointer to the file name statistic file name
	 * @return true if the value is changed, else false
	 */
	bool setUniversPartStatisticFileName(const char* universPartFilename);
	
	/**
	 * prints the head of the parts statistic to the given stream
	 * @see setUniversPartStatisticFileName
	 * @see getUniversPartStatisticFileName
	 * @see setOutUniversPartStatistic
	 * @param statisticStream stream wher to write the parts statistic head to
	 */
	void printUniversPartsStatisticHead( ostream &statisticStream ) const;

	/**
	 * writes the values of the univers to the given output stream, if it exists
	 * @see readUnivers
	 * @param ostream the outputstream ostream to write the univers to
	 * @return if the stream exists true and the actual univers in the stream
	 * 	ostream in a readebel form(integer numbers seperated by ",",";" and "."),
	 * 	false else
	 */
	bool printUnivers( ostream &ostream );

	/**
	 * replaces the actual univers with the univers of the stream, if it exists;
	 * for that deletes the old univers and reads the values of the univers from
	 * the stream (the values should be of the form of printUnivers uses)
	 * @see printUnivers
	 * @param istream the input stream to read the univers from
	 * @return if the stream exists true and this univers is the univers readed from
	 * the stream, else false
	 */
	bool readUnivers( istream &istream );

	/**
	* This method splits this univers into its parts. 
	* The points of the parts are connected to each other and no point in a
	* part is not connected to any other point of the part.
	* This univers will be deleted afterwarts.
	* pre: this univers
	* @return: this univers as its interconnected parts
	*/
	list<TUPart> splitUniversIntoParts();
	
	/**
	* this method writes the statistic for the given universparts into an stream
	* @param universParts the univers parts for which to write the statistic
	* @param partStatistic the output stream, wher to write the statistic to
	* @return true if the statistic is written to the stream, else false
	*/
	bool writeUniversPartStatistic( const list<TUPart> &universParts, ostream &partStatistic);
	
	/**
	* adds the given univers parts to (the end) of this univers
	* @param universParts the universParts to add
	* @return true if the univers parts are added, else false
	*/
	bool addUniversParts( const list<TUPart> &universParts);

	/**
	* This method prints the statistic of the univers parts to the
	* universpart statistic file
	* @return true if the statistic is written, else false
	*/
	bool evaluePartStatistic();
	
	/**
	* Trys to delete parts of the univers that are no more conected to the main part.
	* The main part is the part, wich is the biggest(in number of Distances)
	* under the parts that are not smaler than (maxClass * (biggest Part)) and that
	* has a dimension nearest to dim.
	* @param dim the value of the dimension to be nearest to 
	* @param maxClass the minimum ratio the universes to choos must have (if 1 the bigest univers will allways be choosen)
	* @return the choosen univers as this univers
	*/
	void cutUnivers(const double dim, const double maxClass);

	/**
	 * Makes a transition of the transition diagram with the cPoint poi
	 * (p2 in the diagram) and two neigthbours (includes new cPoints)(p1 and
	 * p3 in the diagram), which are selected with the wich parameter.
	 * @param poi the choosen point of the univers 
	 * @param wich the number of the transition to choos, from the possible
	 *		transitions at the point poi
	 * returns the this univers changed through the transition
	 */
	void evalueTransition( cPoint* poi, unsigned long wich );

	/**
	 * evalue a tick (tick: minimal time change, of the univers);
	 * make a transition for ervery point in the univers
	 * post: this univers changed
	 * @see tick()
	 */
	void tick();

	/**
	 * Evalue a tick, minimal time change, of the univers. For that trans
	 * random choosen points of the univers a random transition is performed.
	 * Points that have no neigthbours are deleted.
	 * post: this univers changed
	 * @see tick()
	 */
	void tick( unsigned long trans );

	/**
	 * Print the head of the statistics to the statistic stream, if it exists.
	 * The diverent rows a seperated by ";".
	 * @param ostream the output stream ostream to print the statistics head to
	 * @return true if the head of the statistics is written to the output 
	 *		stream, else false 
	 */
	bool printStatisticHead( ostream& ostream ) const;

	/**
	 * Print the the statistics of the actual univers and the last transitions
	 * to the statistic stream, if it exists. The diverent rows a seperated by ";".
	 * Prints one line.
	 * @param ostream the output stream ostream to print the actual statistics to
	 * @return true if the actual statistics is written to in the output 
	 * stream, else false*/
	bool printStatistic( ostream& ostream );

	/**
	 * output the the statistics of the actual univers and the last 
	 * transitions	to the consol(cout).
	 * post:  the actual statistics on the console
	 */
	void outputStatistic();

	/**
	 * Evalues the end condition for the univers. Means when the evaluation 
	 * of	the univers is stoped.
	 * case 1: the time iTime is higer than the maximum number of ticks (maxTime,
	 * 	maxTime=0 -> inf) or (the number of points should be checked (it is the
	 * 	checkMaxPoints tick) and it is higher then the maximal number of points
	 * 	(maxPoints, maxPoints=0 -> inf))
	 * @return true if the end condition holds and the univers should be stoped,
	 * 	else false
	 */
	bool endCondition() const;

	/**
	 * Starts the evaluation of the univers. Makes ticks till the end 
	 * condition ( endCondition() ) holds.
	 * post: the this univers changed
	 * @see endCondition()
	 * @see tick()
	 *
	* @param trans number of transitions to evalue in an tick(), if 0 the 
	* 	number of transition is unlimeted is the number of points at the 
	* 	start of the tick
	 */
	void start( unsigned long trans=0 );
	
	/**
	 * the equal realtion for cUnivers
	 * @param univ the univers to compare this univers to
	 * @return true if the univers has same points in the same amount, false else
	 */
	bool operator==( cUnivers &univ );


};

/**
 * outputs this cPoint to the ostream;
 * first comes the name of this cPoint then a ";", the the names of positiv
 * neigbours (for each a ","), then a ";", the the names of negativ
 * neigbours (for each a ","), the a "." and a newline
 * @param tpoi the point to output
 *
 * @param ostream the stream wher to output the point to
 * @return this cPoint in the stream
 */
ostream& operator<<( ostream &ostream, cPoint &tpoi );


#endif
