Exemplo n.º 1
0
Number GoldenSection::findMinimum()
{
	Interval currentInterval;
	currentInterval.leftBorder = m_sourceInterval.leftBorder +
		m_ratio * (m_sourceInterval.rightBorder - m_sourceInterval.leftBorder);
	currentInterval.rightBorder = m_sourceInterval.leftBorder +
		m_sourceInterval.rightBorder - currentInterval.leftBorder;
	Number delta = 0;

	do {
		if (calculateFunction(currentInterval.leftBorder) <= calculateFunction(currentInterval.rightBorder)) {
			m_sourceInterval.rightBorder = currentInterval.rightBorder;
			currentInterval.rightBorder = currentInterval.leftBorder;
			currentInterval.leftBorder = m_sourceInterval.leftBorder +
				m_sourceInterval.rightBorder - currentInterval.leftBorder;
		}
		else {
			m_sourceInterval.leftBorder = currentInterval.leftBorder;
			currentInterval.leftBorder = currentInterval.rightBorder;
			currentInterval.rightBorder = m_sourceInterval.leftBorder +
				m_sourceInterval.rightBorder - currentInterval.rightBorder;
		}

		delta = fabs(m_sourceInterval.leftBorder - m_sourceInterval.rightBorder);
	} while (delta > m_accuracy);

	return (m_sourceInterval.leftBorder + m_sourceInterval.rightBorder) / 2;
}
Exemplo n.º 2
0
Number Integral::findAreaOnInterval(Number left, Number right)
{
	Number middle = left + (right - left) / 2;
	Number functionLeft = calculateFunction(left);
	Number functionMiddle = calculateFunction(middle);
	Number functionRight = calculateFunction(right);
	Number step = right - left;

	return (step / 6.0) * (functionLeft + 4 * functionMiddle + functionRight);
}
Exemplo n.º 3
0
Number Derivative::findSolution(Number point)
{
	Number result = 0;

	result -= calculateFunction(point + 2 * smallNumber(point));
	result += 8 * calculateFunction(point + smallNumber(point));
	result -= 8 * calculateFunction(point - smallNumber(point));
	result += calculateFunction(point - 2 * smallNumber(point));
	result /= 12 * smallNumber(point);

	return result;
}
double Funktion::newtonIntervall(Intervall searchRootHere, Funktion derivate){
    Intervall x(searchRootHere.getInf(),searchRootHere.getSup());
    while(x.getInf()!=x.getSup()){
        x = (x.x_()-calculateFunction(x.x_())/derivate.fInt(x))&&x;
        if(x.getInf()!=x.getInf())
            return NAN;
    }
    return x.getInf();
}
Exemplo n.º 5
0
Number Enumerative::findMinimum()
{
	Number minimumPoint = m_sourceInterval.leftBorder +
		(m_sourceInterval.rightBorder - m_sourceInterval.leftBorder) /
		(m_iterationsCount + 1);
	Number functionMinumum = calculateFunction(minimumPoint);

	for (int i = 1; i <= m_iterationsCount; i++) {
		Number currentPoint = m_sourceInterval.leftBorder + i *
			(m_sourceInterval.rightBorder - m_sourceInterval.leftBorder) /
			(m_iterationsCount + 1);

		if (calculateFunction(currentPoint) < functionMinumum) {
			functionMinumum = calculateFunction(currentPoint);
			minimumPoint = currentPoint;
		}
	}

	return minimumPoint;
}
Intervall Funktion::fInt(Intervall x, double acc=.001){
    double inf = calculateFunction(x.getSup());
    double sup = calculateFunction(x.getSup());
    for(double i=x.getInf();i<x.getSup();i+=acc){
        if(calculateFunction(i)<inf)
            inf = calculateFunction(i);
        else if(calculateFunction(i)>sup)
            sup = calculateFunction(i);
    }
    return Intervall(inf,sup);
}
Exemplo n.º 7
0
QList<Number> HookeJeeves::findMinimum()
{
	QList<Number> currentPoint = m_sourcePoint;

	forever {
		for (int i = 0; i < currentPoint.size(); i++) {
			if (calculateFunction(increaseDirection(currentPoint, i)) < calculateFunction(currentPoint)) {
				currentPoint = increaseDirection(currentPoint, i);
			}
			else if (calculateFunction(decreaseDirection(currentPoint, i)) < calculateFunction(currentPoint)) {
				currentPoint = decreaseDirection(currentPoint, i);
			}
		}

		if (calculateFunction(currentPoint) < calculateFunction(m_sourcePoint)) {
			QList<Number> oldSourcePoint = m_sourcePoint;
			m_sourcePoint = currentPoint;
			for (int i = 0; i < currentPoint.size(); i++) {
				currentPoint[i] = m_sourcePoint[i] + m_accelerationCoefficient * (m_sourcePoint[i] - oldSourcePoint[i]);
			}
		}
		else {
			bool isFinish = true;
			for (int i = 0; i < m_stepSizes.size(); i++) {
				if (m_stepSizes[i] > m_stopValue) {
					isFinish = false;
					m_stepSizes[i] = m_stepSizes[i] / m_decreaseCoefficient;
				}
			}

			if (isFinish) {
				// Exit condition
				return m_sourcePoint;
			}
			else {
				currentPoint = m_sourcePoint;
			}
		}
	}
}
  /** Do MC/simulated annealing to refine parameters
    *
    * Helpful:     double curchi2 = calculateD2TOFFunction(mFunction, domain, values, rawY, rawE);
    */
  double RefinePowderInstrumentParameters2::doSimulatedAnnealing(map<string, Parameter> inparammap)
  {
    // 1. Prepare/initialization
    //    Data structure
    const MantidVec& dataY = m_dataWS->readY(m_wsIndex);

    size_t numpts = dataY.size();

    vector<double> vecY(numpts, 0.0);

    //    Monte Carlo strategy and etc.
    vector<vector<string> > mcgroups;
    setupRandomWalkStrategy(inparammap, mcgroups);

    int randomseed = getProperty("MonteCarloRandomSeed");
    srand(randomseed);

    double temperature = getProperty("AnnealingTemperature");
    if (temperature < 1.0E-10)
      throw runtime_error("Annealing temperature is too low.");

    int maxiterations = getProperty("MonteCarloIterations");
    if (maxiterations <= 0)
      throw runtime_error("Max iteration cannot be 0 or less.");

    //    Book keeping
    map<string, Parameter> parammap;
    duplicateParameters(inparammap, parammap);
    // vector<pair<double, map<string, Parameter> > > bestresults;
    map<string, Parameter> bestresult;
    // size_t maxnumresults = 10;

    // 2. Set up parameters and get initial values
    m_bestChiSq = DBL_MAX;
    m_bestChiSqStep = -1;
    m_bestChiSqGroup = -1;

    double chisq0 = calculateFunction(parammap, vecY);
    double chisq0x = calculateFunctionError(m_positionFunc, m_dataWS, m_wsIndex);
    g_log.notice() << "[DBx510] Starting Chi^2 = " << chisq0 << " (homemade) "
                   << chisq0x << " (Levenber-marquadt)" << endl;

    bookKeepMCResult(parammap, chisq0, -1, -1, bestresult); // bestresults, maxnumresults);

    // 3. Monte Carlo starts
    double chisqx = chisq0;
    int numtotalacceptance = 0;
    int numrecentacceptance = 0;
    int numrecentsteps = 0;

    map<string, Parameter> propparammap; // parameters with proposed value
    duplicateParameters(parammap, propparammap);

    for (int istep = 0; istep < maxiterations; ++istep)
    {
      for (int igroup = 0; igroup < static_cast<int>(mcgroups.size()); ++igroup)
      {
        // a) Propose value
        proposeNewValues(mcgroups[igroup], parammap, propparammap, chisqx); // , prevbetterchi2);

        // b) Calcualte function and chi^2
        double propchisq = calculateFunction(propparammap, vecY);

        /*
        stringstream dbss;
        dbss << "[DBx541] New Chi^2 = " << propchisq << endl;
        vector<string> paramnames = m_positionFunc->getParameterNames();
        for (size_t i = 0; i < paramnames.size(); ++i)
        {
          string parname = paramnames[i];
          double curvalue = parammap[parname].value;
          double propvalue = propparammap[parname].value;
          dbss << parname << ":\t\t" << setw(20) << propvalue << "\t\t<-----\t\t" << curvalue << "\t Delta = "
               << curvalue-propvalue << endl;
        }
        g_log.notice(dbss.str());
        */

        // c) Determine to accept change
        bool acceptpropvalues = acceptOrDenyChange(propchisq, chisqx, temperature);

        // d) Change current chi^2, apply change, and book keep
        if (acceptpropvalues)
        {
          setFunctionParameterValues(m_positionFunc, propparammap);
          chisqx = propchisq;
          bookKeepMCResult(parammap, chisqx, istep, igroup, bestresult); // s, maxnumresults);
        }

        // e) MC strategy control
        ++ numtotalacceptance;
        ++ numrecentacceptance;
        ++ numrecentsteps;
      }

      // f) Annealing
      if (numrecentsteps >= 10)
      {
        double acceptratio = static_cast<double>(numrecentacceptance)/static_cast<double>(numrecentsteps);
        if (acceptratio < 0.2)
        {
          // i) Low acceptance, need to raise temperature
          temperature *= 2.0;
        }
        else if (acceptratio >= 0.8)
        {
          // ii) Temperature too high to accept too much new change
          temperature /= 2.0;
        }

        // iii) Reset counters
        numrecentacceptance = 0;
        numrecentsteps = 0;
      }
    }

    // 4. Apply the best result
    // sort(bestresults.begin(), bestresults.end());
    setFunctionParameterValues(m_positionFunc, bestresult);
    double chisqf = m_bestChiSq;

    g_log.warning() << "[DBx544] Best Chi^2 From MC = " << m_bestChiSq << endl;

    // 5. Use regular minimzer to try to get a better result
    string fitstatus;
    double fitchisq;
    bool goodfit = doFitFunction(m_positionFunc, m_dataWS, m_wsIndex, "Levenberg-MarquardtMD",
                                 1000, fitchisq, fitstatus);

    bool restoremcresult = false;
    if (goodfit)
    {
      map<string, Parameter> nullmap;
      fitchisq = calculateFunction(nullmap, vecY);
      if (fitchisq > chisqf)
      {
        // Fit is unable to achieve a better solution
        restoremcresult = true;
      }
      else
      {
        m_bestChiSq = fitchisq;
      }
    }
    else
    {
      // Fit is bad
      restoremcresult = true;
    }

    g_log.warning() << "[DBx545] Restore MC Result = " << restoremcresult << endl;

    if (restoremcresult)
    {
      setFunctionParameterValues(m_positionFunc, bestresult);
    }
    chisqf = m_bestChiSq;

    // 6. Final result
    double chisqfx = calculateFunctionError(m_positionFunc, m_dataWS, m_wsIndex);
    map<string, Parameter> emptymap;
    double chisqf0 = calculateFunction(emptymap, vecY);
    g_log.notice() << "Best Chi^2 (L-V) = " << chisqfx << ", (homemade) = " << chisqf0 << endl;
    g_log.warning() << "Data Size = " << m_dataWS->readX(m_wsIndex).size() << ", Number of parameters = "
                    << m_positionFunc->getParameterNames().size() << endl;

    return chisqf;
  }