ROOT logo
// $Id: WarmAmoeba.cxx 2456 2010-10-17 18:31:40Z matevz $

#include "WarmAmoeba.h"
#include "WarmAmoeba.c7"

#include <Gled/GledMirDefs.h>
#include <Gled/GledOperatorDefs.h>

#include <TMath.h>

ClassImp(WarmAmoeba);

/**************************************************************************/
// private

void WarmAmoeba::_init()
{
  hTrueMaster = 0; m_P = 0;

  mSeed = 0;
  mFTol = 1e-12;
  mTFactor = 3; mAlpha = 1.5;
  mMovesPerT = 1000; mNumSteps = 100;
  mT0 = mT = 0;
  mYBest = mYLast = 0;
}

void WarmAmoeba::_calc_psum()
{
  for (Int_t i = 0; i < m_n; ++i)
  {
    m_Psum(i) = 0;
    for(Int_t j = 0; j <= m_n; ++j)
    {
      m_Psum(i) += P(j,i);
    }
  }
}

void WarmAmoeba::_export_algo_values(Operator::Arg* op_arg, bool bestp)
{
  OP_EXE_OR_SP_MIR(this, SetT, m_T);
  OP_EXE_OR_SP_MIR(this, SetYLast, m_Y(0u));
  OP_EXE_OR_SP_MIR(this, SetYBest, m_y_best);
  if (bestp)
  {
    OP_EXE_OR_SP_MIR_SATURN(mSaturn, hTrueMaster, SetState, m_PBest);
  }
  else
  {
    OP_EXE_OR_SP_MIR_SATURN(mSaturn, hTrueMaster, SetState, m_P[0]);
  }
}

/**************************************************************************/
// protected

void WarmAmoeba::InitZStuff()
{
  m_Psum.ResizeTo(m_n);
  delete [] m_P;
  m_P = new TVectorF[m_n+1];
  for (Int_t i = 0; i <= m_n; ++i)  (m_P[i]).ResizeTo(m_n);
  m_Y.ResizeTo(m_n+1);
  m_PBest.ResizeTo(m_n);
}

Float_t WarmAmoeba::Ooze(Int_t ihi, Float_t& yhi, Float_t fac)
{
  TVectorF ptry(m_n);
  Float_t fac1 = (1-fac)/m_n;
  Float_t fac2 = fac1 - fac;
  for (Int_t j = 0; j < m_n; ++j)
  {
    ptry(j) = m_Psum(j)*fac1 - P(ihi,j)*fac2;
  }
  Float_t ytry = hTrueMaster->Foon(ptry);
  if (ytry <= m_y_best)
  {
    m_PBest = ptry;
    m_y_best = ytry;
  }
  Float_t yflu = ytry + m_T*TMath::Log(mRanGen.Rndm());
  if (yflu  < yhi)
  {
    m_Y(ihi) = ytry; yhi = yflu;
    for (Int_t j = 0; j < m_n; ++j)
    {
      m_Psum(j) += ptry(j) - P(ihi,j);
      P(ihi,j) = ptry(j);
    }
  }
  return yflu;
}

void WarmAmoeba::WAMove()
{
  Float_t ynhi, ylo, yhi, yt;
  _calc_psum();
  while(true)
  {
    Int_t ilo=0, ihi=1;
    ynhi = ylo = m_Y(0u) - m_T*TMath::Log(mRanGen.Rndm());
    yhi = m_Y(1u) - m_T*TMath::Log(mRanGen.Rndm());
    if (ylo > yhi)
    {
      ihi = 0; ilo = 1;
      ynhi = yhi; yhi = ylo; ylo = ynhi;
    }
    for (Int_t i = 2; i <= m_n; ++i)
    {
      yt = m_Y(i) - m_T*TMath::Log(mRanGen.Rndm());
      if (yt <= ylo)
      {
        ilo = i; ylo = yt;
      }
      if (yt > yhi)
      {
        ihi = i; ynhi = yhi; yhi = yt;
      }
      else
      {
        ynhi = yt;
      }
    }
    Float_t rtol = 2*TMath::Abs(yhi-ylo) / (TMath::Abs(yhi) + TMath::Abs(ylo));
    if (rtol < mFTol || m_iter < 0)
    {
      Float_t swap = m_Y(0u); m_Y(0u) = m_Y(ilo); m_Y(ilo) = swap;
      for (Int_t n = 0; n < m_n; ++n)
      {
	swap = P(0u,n); P(0u,n) = P(ilo,n); P(ilo,n) = swap;
      }
      break;
    }
    m_iter -= 2;
    Float_t ytry = Ooze(ihi, yhi, -1);
    if (ytry <= ylo)
    {
      ytry = Ooze(ihi, yhi, 2);
    }
    else if (ytry >- ynhi)
    {
      Float_t ysave = yhi;
      ytry = Ooze(ihi, yhi, 0.5);
      if (ytry >= ysave)
      {
	for (Int_t i = 0; i < m_n; ++i)
        {
	  if (i != ilo)
          {
	    for (Int_t j = 0; j < m_n; ++j)
            {
	      m_Psum(j) = 0.5*(P(i,j) + P(ilo,j));
	      P(i,j) = m_Psum(j);
	    }
	    m_Y(i) = hTrueMaster->Foon(m_Psum);
	  }
	}
	m_iter -= m_n;
	_calc_psum();
      }
    }
    else
    {
      m_iter++;
    }
  }
}

/**************************************************************************/
// public
/**************************************************************************/

WarmAmoeba::WarmAmoeba(const Text_t* n, const Text_t* t) :
  Eventor(n,t), mWA_Master(0), mRanGen(0)
{ _init(); }

WarmAmoeba::WarmAmoeba(ZGlass* m, const Text_t* n, const Text_t* t) :
  Eventor(n,t), mWA_Master(m), mRanGen(0)
{ _init(); }

WarmAmoeba::~WarmAmoeba()
{
  delete [] m_P;
}

/**************************************************************************/
/**************************************************************************/

Operator::Arg* WarmAmoeba::PreDance(Operator::Arg* op_arg)
{
  op_arg = Eventor::PreDance(op_arg);

  hTrueMaster = dynamic_cast<WarmAmoebaMaster*>(*mWA_Master);
  if(!hTrueMaster) {
    ISerr("WarmAmoeba::PreDance master not a WarmAmoebaMaster");
    delete op_arg;
    return 0;
  }
  mRanGen.SetSeed(mSeed);
  { // Init state
    TVectorF *v = hTrueMaster->InitialState(mRanGen);
    if(v->GetNoElements() < 3) {
      ISerr("WarmAmoeba::PreDance Need at least 3 parameters for amoeba");
      delete op_arg;
      return 0;
    }
    m_n = v->GetNoElements();
    OP_EXE_OR_SP_MIR(this, SetN, m_n);
    InitZStuff();
    m_P[0] = *v; m_Y(0u) = hTrueMaster->Foon(m_P[0]);
    delete v;
  }
  { // Get perturbations
    TVectorF *v = hTrueMaster->InitialPerturbations(mRanGen);
    for (Int_t i = 1; i <= m_n; ++i)
    {
      m_P[i] = m_P[0]; P(i, i-1) += (*v)(i-1);
      m_Y(i) = hTrueMaster->Foon(m_P[i]);
    }
    delete v;
  }
  // Estimate temperature
  Float_t t=0;
  for (Int_t i = 1; i <= m_n; ++i) t += TMath::Abs(m_Y(0u) - m_Y(i));
  m_T = t/m_n;
  m_y_best = mYBest = 10*m_Y(0u); // Large enough
  mYLast = m_Y(0u);
  m_T0 = mTFactor * t/m_n;

  mLocBeatsDone = 0;
  OP_EXE_OR_SP_MIR(this, SetBeatsDone, 0);
  OP_EXE_OR_SP_MIR(this, SetBeatsToDo, mNumSteps);
  OP_EXE_OR_SP_MIR(this, SetT0, m_T0);
  _export_algo_values(op_arg);

  return Eventor::PreDance(op_arg);
}

void WarmAmoeba::PostDance(Operator::Arg* op_arg)
{
  Eventor::PostDance(op_arg);
  _export_algo_values(op_arg, true);
}

/**************************************************************************/

void WarmAmoeba::PostBeat(Operator::Arg* op_arg) throw(Operator::Exception)
{
  Eventor::PostBeat(op_arg);
  if (mStampInterval == 0 || mLocBeatsDone % mStampInterval == 0)
  {
    _export_algo_values(op_arg);
  }
}

/**************************************************************************/

void WarmAmoeba::Operate(Operator::Arg* op_arg)
{
  Eventor::PreOperate(op_arg);

  m_T = m_T0*TMath::Power(1 - (Float_t)mLocBeatsDone/(mBeatsToDo-1), mAlpha);
  m_iter = mMovesPerT;
  WAMove();

  Eventor::PostOperate(op_arg);
}
 WarmAmoeba.cxx:1
 WarmAmoeba.cxx:2
 WarmAmoeba.cxx:3
 WarmAmoeba.cxx:4
 WarmAmoeba.cxx:5
 WarmAmoeba.cxx:6
 WarmAmoeba.cxx:7
 WarmAmoeba.cxx:8
 WarmAmoeba.cxx:9
 WarmAmoeba.cxx:10
 WarmAmoeba.cxx:11
 WarmAmoeba.cxx:12
 WarmAmoeba.cxx:13
 WarmAmoeba.cxx:14
 WarmAmoeba.cxx:15
 WarmAmoeba.cxx:16
 WarmAmoeba.cxx:17
 WarmAmoeba.cxx:18
 WarmAmoeba.cxx:19
 WarmAmoeba.cxx:20
 WarmAmoeba.cxx:21
 WarmAmoeba.cxx:22
 WarmAmoeba.cxx:23
 WarmAmoeba.cxx:24
 WarmAmoeba.cxx:25
 WarmAmoeba.cxx:26
 WarmAmoeba.cxx:27
 WarmAmoeba.cxx:28
 WarmAmoeba.cxx:29
 WarmAmoeba.cxx:30
 WarmAmoeba.cxx:31
 WarmAmoeba.cxx:32
 WarmAmoeba.cxx:33
 WarmAmoeba.cxx:34
 WarmAmoeba.cxx:35
 WarmAmoeba.cxx:36
 WarmAmoeba.cxx:37
 WarmAmoeba.cxx:38
 WarmAmoeba.cxx:39
 WarmAmoeba.cxx:40
 WarmAmoeba.cxx:41
 WarmAmoeba.cxx:42
 WarmAmoeba.cxx:43
 WarmAmoeba.cxx:44
 WarmAmoeba.cxx:45
 WarmAmoeba.cxx:46
 WarmAmoeba.cxx:47
 WarmAmoeba.cxx:48
 WarmAmoeba.cxx:49
 WarmAmoeba.cxx:50
 WarmAmoeba.cxx:51
 WarmAmoeba.cxx:52
 WarmAmoeba.cxx:53
 WarmAmoeba.cxx:54
 WarmAmoeba.cxx:55
 WarmAmoeba.cxx:56
 WarmAmoeba.cxx:57
 WarmAmoeba.cxx:58
 WarmAmoeba.cxx:59
 WarmAmoeba.cxx:60
 WarmAmoeba.cxx:61
 WarmAmoeba.cxx:62
 WarmAmoeba.cxx:63
 WarmAmoeba.cxx:64
 WarmAmoeba.cxx:65
 WarmAmoeba.cxx:66
 WarmAmoeba.cxx:67
 WarmAmoeba.cxx:68
 WarmAmoeba.cxx:69
 WarmAmoeba.cxx:70
 WarmAmoeba.cxx:71
 WarmAmoeba.cxx:72
 WarmAmoeba.cxx:73
 WarmAmoeba.cxx:74
 WarmAmoeba.cxx:75
 WarmAmoeba.cxx:76
 WarmAmoeba.cxx:77
 WarmAmoeba.cxx:78
 WarmAmoeba.cxx:79
 WarmAmoeba.cxx:80
 WarmAmoeba.cxx:81
 WarmAmoeba.cxx:82
 WarmAmoeba.cxx:83
 WarmAmoeba.cxx:84
 WarmAmoeba.cxx:85
 WarmAmoeba.cxx:86
 WarmAmoeba.cxx:87
 WarmAmoeba.cxx:88
 WarmAmoeba.cxx:89
 WarmAmoeba.cxx:90
 WarmAmoeba.cxx:91
 WarmAmoeba.cxx:92
 WarmAmoeba.cxx:93
 WarmAmoeba.cxx:94
 WarmAmoeba.cxx:95
 WarmAmoeba.cxx:96
 WarmAmoeba.cxx:97
 WarmAmoeba.cxx:98
 WarmAmoeba.cxx:99
 WarmAmoeba.cxx:100
 WarmAmoeba.cxx:101
 WarmAmoeba.cxx:102
 WarmAmoeba.cxx:103
 WarmAmoeba.cxx:104
 WarmAmoeba.cxx:105
 WarmAmoeba.cxx:106
 WarmAmoeba.cxx:107
 WarmAmoeba.cxx:108
 WarmAmoeba.cxx:109
 WarmAmoeba.cxx:110
 WarmAmoeba.cxx:111
 WarmAmoeba.cxx:112
 WarmAmoeba.cxx:113
 WarmAmoeba.cxx:114
 WarmAmoeba.cxx:115
 WarmAmoeba.cxx:116
 WarmAmoeba.cxx:117
 WarmAmoeba.cxx:118
 WarmAmoeba.cxx:119
 WarmAmoeba.cxx:120
 WarmAmoeba.cxx:121
 WarmAmoeba.cxx:122
 WarmAmoeba.cxx:123
 WarmAmoeba.cxx:124
 WarmAmoeba.cxx:125
 WarmAmoeba.cxx:126
 WarmAmoeba.cxx:127
 WarmAmoeba.cxx:128
 WarmAmoeba.cxx:129
 WarmAmoeba.cxx:130
 WarmAmoeba.cxx:131
 WarmAmoeba.cxx:132
 WarmAmoeba.cxx:133
 WarmAmoeba.cxx:134
 WarmAmoeba.cxx:135
 WarmAmoeba.cxx:136
 WarmAmoeba.cxx:137
 WarmAmoeba.cxx:138
 WarmAmoeba.cxx:139
 WarmAmoeba.cxx:140
 WarmAmoeba.cxx:141
 WarmAmoeba.cxx:142
 WarmAmoeba.cxx:143
 WarmAmoeba.cxx:144
 WarmAmoeba.cxx:145
 WarmAmoeba.cxx:146
 WarmAmoeba.cxx:147
 WarmAmoeba.cxx:148
 WarmAmoeba.cxx:149
 WarmAmoeba.cxx:150
 WarmAmoeba.cxx:151
 WarmAmoeba.cxx:152
 WarmAmoeba.cxx:153
 WarmAmoeba.cxx:154
 WarmAmoeba.cxx:155
 WarmAmoeba.cxx:156
 WarmAmoeba.cxx:157
 WarmAmoeba.cxx:158
 WarmAmoeba.cxx:159
 WarmAmoeba.cxx:160
 WarmAmoeba.cxx:161
 WarmAmoeba.cxx:162
 WarmAmoeba.cxx:163
 WarmAmoeba.cxx:164
 WarmAmoeba.cxx:165
 WarmAmoeba.cxx:166
 WarmAmoeba.cxx:167
 WarmAmoeba.cxx:168
 WarmAmoeba.cxx:169
 WarmAmoeba.cxx:170
 WarmAmoeba.cxx:171
 WarmAmoeba.cxx:172
 WarmAmoeba.cxx:173
 WarmAmoeba.cxx:174
 WarmAmoeba.cxx:175
 WarmAmoeba.cxx:176
 WarmAmoeba.cxx:177
 WarmAmoeba.cxx:178
 WarmAmoeba.cxx:179
 WarmAmoeba.cxx:180
 WarmAmoeba.cxx:181
 WarmAmoeba.cxx:182
 WarmAmoeba.cxx:183
 WarmAmoeba.cxx:184
 WarmAmoeba.cxx:185
 WarmAmoeba.cxx:186
 WarmAmoeba.cxx:187
 WarmAmoeba.cxx:188
 WarmAmoeba.cxx:189
 WarmAmoeba.cxx:190
 WarmAmoeba.cxx:191
 WarmAmoeba.cxx:192
 WarmAmoeba.cxx:193
 WarmAmoeba.cxx:194
 WarmAmoeba.cxx:195
 WarmAmoeba.cxx:196
 WarmAmoeba.cxx:197
 WarmAmoeba.cxx:198
 WarmAmoeba.cxx:199
 WarmAmoeba.cxx:200
 WarmAmoeba.cxx:201
 WarmAmoeba.cxx:202
 WarmAmoeba.cxx:203
 WarmAmoeba.cxx:204
 WarmAmoeba.cxx:205
 WarmAmoeba.cxx:206
 WarmAmoeba.cxx:207
 WarmAmoeba.cxx:208
 WarmAmoeba.cxx:209
 WarmAmoeba.cxx:210
 WarmAmoeba.cxx:211
 WarmAmoeba.cxx:212
 WarmAmoeba.cxx:213
 WarmAmoeba.cxx:214
 WarmAmoeba.cxx:215
 WarmAmoeba.cxx:216
 WarmAmoeba.cxx:217
 WarmAmoeba.cxx:218
 WarmAmoeba.cxx:219
 WarmAmoeba.cxx:220
 WarmAmoeba.cxx:221
 WarmAmoeba.cxx:222
 WarmAmoeba.cxx:223
 WarmAmoeba.cxx:224
 WarmAmoeba.cxx:225
 WarmAmoeba.cxx:226
 WarmAmoeba.cxx:227
 WarmAmoeba.cxx:228
 WarmAmoeba.cxx:229
 WarmAmoeba.cxx:230
 WarmAmoeba.cxx:231
 WarmAmoeba.cxx:232
 WarmAmoeba.cxx:233
 WarmAmoeba.cxx:234
 WarmAmoeba.cxx:235
 WarmAmoeba.cxx:236
 WarmAmoeba.cxx:237
 WarmAmoeba.cxx:238
 WarmAmoeba.cxx:239
 WarmAmoeba.cxx:240
 WarmAmoeba.cxx:241
 WarmAmoeba.cxx:242
 WarmAmoeba.cxx:243
 WarmAmoeba.cxx:244
 WarmAmoeba.cxx:245
 WarmAmoeba.cxx:246
 WarmAmoeba.cxx:247
 WarmAmoeba.cxx:248
 WarmAmoeba.cxx:249
 WarmAmoeba.cxx:250
 WarmAmoeba.cxx:251
 WarmAmoeba.cxx:252
 WarmAmoeba.cxx:253
 WarmAmoeba.cxx:254
 WarmAmoeba.cxx:255
 WarmAmoeba.cxx:256
 WarmAmoeba.cxx:257
 WarmAmoeba.cxx:258
 WarmAmoeba.cxx:259
 WarmAmoeba.cxx:260
 WarmAmoeba.cxx:261
 WarmAmoeba.cxx:262
 WarmAmoeba.cxx:263
 WarmAmoeba.cxx:264
 WarmAmoeba.cxx:265
 WarmAmoeba.cxx:266
 WarmAmoeba.cxx:267
 WarmAmoeba.cxx:268
 WarmAmoeba.cxx:269