Beispiel #1
0
  double Basic_MCT2_332_Calculator::mct2_332_Sq(const LorentzTransverseVector& visA,
					       const LorentzTransverseVector& visB,
					       const TwoVector& ptmiss,
					       const double mEachInvisible){


    mCT2Fcn theFCN(ptmiss.px(),
	 	   ptmiss.py(),
		   mEachInvisible,
		   visA.px(),
		   visA.py(),
		   visA.mass(),
		   visB.px(),
		   visB.py(),
		   visB.mass());

    const double massScale = (
			      ptmiss.pt() +
			      mEachInvisible +
			      visA.pt()  +
			      visA.mass() +
			      visB.pt() +
			      visB.mass()
			      )/6.0;
    // DANG! Try to get rid of Minuit output:
    //std::ofstream    DANG_log("/dev/null");
    //std::streambuf * DANG_save = std::cerr.rdbuf();
    //if (DANG_log.is_open()) {
    //  std::cerr.rdbuf(DANG_log.rdbuf());
    // }

    double guessx = 0.5*(ptmiss.px());
    double guessy = 0.5*(ptmiss.py());
    
    MnUserParameters upar;
    upar.Add("etx", guessx, 0.02*massScale); 
    upar.Add("ety", guessy, 0.02*massScale);
    const int highQuality=2;    

    // Usually migrad produces the best minumum.
    // But when the minimum is in a fold, migrad can fail badly.
    // On the fold, simplex does well.  We therefore do both separately
    // and record the answer of the one that did best.
    
    // Further to the above notes, it now seems that by choosing the massScale sensibly, and by making the "tolerance" (the second argument to the call that extracts the FunctionMinimum below) much smaller, the simplex algorithm seems to work so well that we don't need the migrad algorithm.  This is good news, as the migrad algorithm produces lots of error output that we can't get rid of.

    MnSimplex simplex(theFCN, upar, highQuality);
    FunctionMinimum minS = simplex(0,massScale*0.000001);
    //const double etxAtMin = minS.UserState().Value("etx");
    //const double etyAtMin = minS.UserState().Value("ety");
    //MnMigrad migrad(theFCN, upar, highQuality);
    //FunctionMinimum minM = migrad(0,massScale*0.000001);
    //const double best = fmin(minS.Fval(), minM.Fval());
    const double best = minS.Fval();

    // DANG! Undoing our attempt to get rid of Minuit output:
    //if (DANG_log.is_open()) {
    //  std::cerr.rdbuf(DANG_save);
    //}

    return best;    
  }
Beispiel #2
0
//Use Migrad to minimise the given function
void FumiliWrapper::Minimise()
{
	ParameterSet * newParameters = RapidFunction->GetParameterSet();
	vector<string> allNames = newParameters->GetAllNames();
	//	int numParams = allNames.size();

	/*
	// Fill a vector of doubles for each set of physics parameters that you
	// want to sample. What about case where Apara_sq + Aperp_sq > 1?
	vector< vector<double> > positions;
	PhysicsBottle* bottle = NewFunction->GetPhysicsBottle();
	ParameterSet* parameters = bottle->GetParameterSet();
	vector<string> names = parameters->GetAllNames();
	double nsteps = 1;
	for( int k = 0; k < names.size(); ++k)
	{
	for( int j = 0; j < nsteps; ++j)
	{
	vector<double> tempPos;
	for( int i = 0; i < names.size(); ++i )
	{
	double value;
	if ( i != k )
	{
	value = parameters->GetPhysicsParameter(names[i])->GetValue();
	}
	else
	{
	double min = parameters->GetPhysicsParameter(names[i])->GetMinimum();
	double max = parameters->GetPhysicsParameter(names[i])->GetMaximum();
	double step = (max - min)/nsteps;
	value = min + j * step;
	}
	tempPos.push_back(value);
	}
	positions.push_back(tempPos);
	}
	}
	*/

	// Fill a vector of doubles for each set of observables
	vector< vector<double> > positions;
	PhysicsBottle* bottle = RapidFunction->GetPhysicsBottle();
	PhaseSpaceBoundary* boundary = bottle->GetResultDataSet(0)->GetBoundary();
	vector<string> names = boundary->GetAllNames();

	vector<double> observableSteps;
	int nsteps = 10;

	// Could make this faster...
	for ( int step = 0; step < nsteps; ++step)
	{
		vector<double> tempPos;
		for( unsigned int observable = 0; observable < names.size(); ++observable )
		{
			if ( !boundary->GetConstraint(names[observable])->IsDiscrete() )
			{
				double min = boundary->GetConstraint(names[observable])->GetMinimum();
				double max = boundary->GetConstraint(names[observable])->GetMinimum();
				double delta = (max - min)/nsteps;
				double position = min + step*delta;
				tempPos.push_back( position );
			}
			else
			{
				double value = boundary->GetConstraint(names[observable])->CreateObservable()->GetValue();
				tempPos.push_back( value );
			}
		}
		positions.push_back(tempPos);
	}

	// Now, get the FumiliFCNBase function which will be passed to the Fumili minimiser
	FumiliStandardMaximumLikelihoodFCN fumFCN( *function, positions );

	// Setup the minimiser
	MnFumiliMinimize fumili( fumFCN, *( function->GetMnUserParameters() ), (unsigned)Quality);//MINUIT_QUALITY);

	// Do the minimisation
	FunctionMinimum minimum = fumili( (unsigned)maxSteps, bestTolerance );//(int)MAXIMUM_MINIMISATION_STEPS, FINAL_GRADIENT_TOLERANCE );

	// Once we have the FunctionMinimum, code same as in other Wrappers
	//Create the fit results
	const MnUserParameters * minimisedParameters = &minimum.UserParameters();
	ResultParameterSet * fittedParameters = new ResultParameterSet( allNames );
	for ( unsigned int nameIndex = 0; nameIndex < allNames.size(); ++nameIndex)
	{
		string parameterName = allNames[nameIndex];
		PhysicsParameter * oldParameter = newParameters->GetPhysicsParameter( parameterName );
		double parameterValue = minimisedParameters->Value( parameterName.c_str() );
		double parameterError = minimisedParameters->Error( parameterName.c_str() );

		fittedParameters->SetResultParameter( parameterName, parameterValue, oldParameter->GetOriginalValue(), parameterError,
				-oldParameter->GetMinimum(), oldParameter->GetMaximum(),
				oldParameter->GetType(), oldParameter->GetUnit() );
	}

	int fitStatus;
	if ( !minimum.HasCovariance() )
	{
		fitStatus = 0;
	}
	else if ( !minimum.HasAccurateCovar() )
	{
		fitStatus = 1;
	}
	else if ( minimum.HasMadePosDefCovar() )
	{
		fitStatus = 2;
	}
	else
	{
		fitStatus = 3;
	}

	PhysicsBottle* newBottle = RapidFunction->GetPhysicsBottle();
	fitResult = new FitResult( minimum.Fval(), fittedParameters, fitStatus, newBottle  );
}