Пример #1
0
  bool MLP::calcGradient(const dmatrix& inputs,
                         const ivector& ids,
                         dvector& grad) {

    if (inputs.rows() != ids.size()) {
      setStatusString("Number of vectors not consistent with number of ids");
      return false;
    }

    dvector tmp;
    int i;
    double tmpError;

    totalError = 0;
    calcGradient(inputs.getRow(0),ids.at(0),grad);
    computeActualError(ids.at(0),totalError);

    for (i=1;i<inputs.rows();++i) {
      calcGradient(inputs.getRow(i),ids.at(i),tmp);
      computeActualError(ids.at(i),tmpError);
      grad.add(tmp);
      totalError+=tmpError;
    }

    return true;
  }
Пример #2
0
void demoplaybackstep()
{
    while(demoplayback && lastmillis>=playbacktime)
    {
        int len = gzgeti();
        if(len<1 || len>MAXTRANS)
        {
            conoutf("error: huge packet during demo play (%d)", len);
            stopreset();
            return;
        };
        uchar buf[MAXTRANS];
        gzread(f, buf, len);
        localservertoclient(buf, len);  // update game state
        
        dynent *target = players[democlientnum];
        assert(target); 
        
		int extras;
        if(extras = gzget())     // read additional client side state not present in normal network stream
        {
            target->gunselect = gzget();
            target->lastattackgun = gzget();
            target->lastaction = scaletime(gzgeti());
            target->gunwait = gzgeti();
            target->health = gzgeti();
            target->armour = gzgeti();
            target->armourtype = gzget();
            loopi(NUMGUNS) target->ammo[i] = gzget();
            target->state = gzget();
            target->lastmove = playbacktime;
			if(bdamage = gzgeti()) damageblend(bdamage);
			if(ddamage = gzgeti()) { gzgetv(dorig); particle_splash(3, ddamage, 1000, dorig); };
            // FIXME: set more client state here
        };
        
        // insert latest copy of player into history
        if(extras && (playerhistory.empty() || playerhistory.last()->lastupdate!=playbacktime))
        {
            dynent *d = newdynent();
            *d = *target;
            d->lastupdate = playbacktime;
            playerhistory.add(d);
            if(playerhistory.length()>20)
            {
                zapdynent(playerhistory[0]);
                playerhistory.remove(0);
            };
        };
        
        readdemotime();
    };
    
    if(demoplayback)
    {
        int itime = lastmillis-demodelaymsec;
        loopvrev(playerhistory) if(playerhistory[i]->lastupdate<itime)      // find 2 positions in history that surround interpolation time point
        {
            dynent *a = playerhistory[i];
            dynent *b = a;
            if(i+1<playerhistory.length()) b = playerhistory[i+1];
            *player1 = *b;
            if(a!=b)                                // interpolate pos & angles
            {
				dynent *c = b;
				if(i+2<playerhistory.length()) c = playerhistory[i+2];
				dynent *z = a;
				if(i-1>=0) z = playerhistory[i-1];
				//if(a==z || b==c) printf("* %d\n", lastmillis);
				float bf = (itime-a->lastupdate)/(float)(b->lastupdate-a->lastupdate);
				fixwrap(a, player1);
				fixwrap(c, player1);
				fixwrap(z, player1);
				vdist(dist, v, z->o, c->o);
				if(dist<16)		// if teleport or spawn, dont't interpolate
				{
					catmulrom(z->o, a->o, b->o, c->o, bf, player1->o);
					catmulrom(*(vec *)&z->yaw, *(vec *)&a->yaw, *(vec *)&b->yaw, *(vec *)&c->yaw, bf, *(vec *)&player1->yaw);
				};
				fixplayer1range();
			};
            break;
        };
        //if(player1->state!=CS_DEAD) showscores(false);
    };
};
Пример #3
0
  /*
   * line search computes the eta scalar factor at which the error
   * is minimized.  It begins at the actual weight and follows the given
   * direction.
   */
  bool MLP::lineSearch(const dmatrix& inputs,
                       const ivector& ids,
                       const dvector& direction,
                       double& xmin,
                       dvector& newWeights) const {

    // following algorithms are based on Press, W.H. et.al. Numerical
    // Recipies in C. Chapter 10, Minimization or Maximization of
    // Functions. pp. 397ff

    static const double gold = 1.618034; // golden mean
    static const double glimit = 100.0;  // maximum magnification
                                         // allowed for parabolic-fit
                                         // step
    static const double tiny = 1.0e-20;
    static const int itmax = 100; // maximum allowed number of
                                  // iterations to find minimum
    static const double cgold = 0.3819660; // golden ration
    static const double zeps = 1.0e-10; // small number that protects
                                        // against trying to achieve
                                        // fractional accuracy for a
                                        // minimum that happens to be
                                        // exaclty 0


    const parameters& param = getParameters();
    const int layers = param.hiddenUnits.size()+1;
    std::vector<dmatrix> mWeights(layers);
    newWeights.copy(weights);
    updateWeightIndices(newWeights,mWeights);

    // -----------------------------------------------------------------------
    //  Initial Bracket
    // -----------------------------------------------------------------------

    double ax(0.0),bx(1.0),cx;
    double fa,fb,fc;
    double ulim,u,r,q,fu,dum;

    // evaluate error at eta=0 and eta=1
    computeTotalError(mWeights,inputs,ids,fa);
    newWeights.add(direction);
    computeTotalError(mWeights,inputs,ids,fb);

    if (fb > fa) { // switch roles of a and b so that we can go
                   // downhill in the direction from a to b
      ax=1.0;
      bx=0.0;
      dum=fa; fa=fb; fb=dum;
    }

    // first guess for c:
    cx = bx + gold*(bx-ax);
    newWeights.addScaled(weights,cx,direction);
    computeTotalError(mWeights,inputs,ids,fc);

    while (fb>fc) { // keep returning here until we bracket
      r=(bx-ax)*(fb-fc);  // Compute u by parabolic extrapolation from a,b,c.
      q=(bx-cx)*(fb-fa);
      if (q>r) {          // tiny is used to prevent any posible division by 0
        u=bx-((bx-cx)*q-(bx-ax)*r)/(2.0*(max(q-r,tiny)));
      } else {
        u=bx-((bx-cx)*q-(bx-ax)*r)/(-2.0*(max(r-q,tiny)));
      }

      ulim=bx+glimit*(cx-bx);
      // We won't go farther than this.  Test various possibilities:
      if ((bx-u)*(u-cx) > 0.0) {
        newWeights.addScaled(weights,u,direction);
        computeTotalError(mWeights,inputs,ids,fu);
        if (fu < fc) { // Got a minimum between b and c
          ax=bx;
          bx=u;
          fa=fb;
          fb=fu;
          break;
        } else if (fu > fb) { // Got a minimum between a and u
          cx=u;
          fc=fu;
          break;
        }
        u=cx+gold*(cx-bx); // Parabolic fit was no use. Use default
                           // magnification
        newWeights.addScaled(weights,u,direction);
        computeTotalError(mWeights,inputs,ids,fu);
      } else if ((cx-u)*(u-ulim) > 0.0) {
        // Parabolic fit is between c and its allowed limit.
        newWeights.addScaled(weights,u,direction);
        computeTotalError(mWeights,inputs,ids,fu);
        if (fu < fc) {
          bx=cx;
          cx=u;
          u=cx+gold*(cx-bx);
          fb=fc;
          fc=fu;
          newWeights.addScaled(weights,u,direction);
          computeTotalError(mWeights,inputs,ids,fu);
        }
      } else if ((u-ulim)*(ulim-cx) >= 0.0) { // Limit parabolic u to
                                             // maximum allowed value
        u=ulim;
        newWeights.addScaled(weights,u,direction);
        computeTotalError(mWeights,inputs,ids,fu);
      } else { // Reject parabolic u, use default magnification
        u=cx+gold*(cx-bx);
        newWeights.addScaled(weights,u,direction);
        computeTotalError(mWeights,inputs,ids,fu);
      }

      // Eliminate oldest point and continue
      ax=bx;
      bx=cx;
      cx=u;
      fa=fb;
      fb=fc;
      fc=fu;
    }

    // -----------------------------------------------------------------------
    //  Line search: Brent's method
    // -----------------------------------------------------------------------

    // fractional precision of found minimum
    static const double tol =
      2.0*sqrt(std::numeric_limits<double>::epsilon());
    double fv,fw,fx,etemp;
    double p,tol1,tol2,v,w,x,xm,a,b,d=0.0;
    int iter;

    // This will be the distance moved on the step before last
    double e=0.0;
    // a and b must be in ascending order, but input abscissas need not be.
    if (ax < cx) {
      a = ax;
      b = cx;
    } else {
      a = cx;
      b = ax;
    }
    // Initializations...
    x=w=v=bx;
    fw=fv=fx=fb;

    for (iter=1;iter<=itmax;++iter) { // main loop
      xm=0.5*(a+b);
      tol2=2.0*(tol1=tol*abs(x)+zeps);
      // test for done here
      if (abs(x-xm) <= (tol2-0.5*(b-a))) {
        xmin = x;
        newWeights.addScaled(weights,xmin,direction);
        return true;
      }
      if (abs(e) > tol1) {
        r=(x-w)*(fx-fv);
        q=(x-v)*(fx-fw);
        p=(x+v)*q - (x-w)*r;
        q=2.0*(q-r);
        if (q > 0.0) p = -p;
        q=abs(q);
        etemp=e;
        e=d;
        if (abs(p) >= abs(0.5*q*etemp) ||
            p <= q*(a-x) ||
            p >= q*(b-x)) {
          d = cgold*(e = (x >= xm ? a-x : b-x));
        }

        // The above conditions determine the acceptability of the
        // parabolic fit.  Here we take the golden section step into
        // the larger of the two segments

        else {
          d=p/q;
          u=x+d;
          if (u-a < tol2 || b-u < tol2) {
            d=(xm>=x)?abs(tol1):-abs(tol1);
          }
        }
      } else {
        d = cgold*(e=(x>=xm ? a-x : b-x));
      }
      u=(abs(d) >= tol1 ? x+d : x+(d>0.0?abs(tol1):-abs(tol1)));
      // This is the one function evaluation per iteration
      newWeights.addScaled(weights,u,direction);
      computeTotalError(mWeights,inputs,ids,fu);

      // Now decide what to do with our function evaluation
      if (fu < fx) {
        if (u>=x) a=x; else b=x;
        // Housekeeping follows:
        v=w;
        w=x;
        x=u;
        fv=fw;
        fw=fx;
        fx=fu;
      } else {
        if (u<x) a=u; else b=u;
        if (fu <= fw || w == x) {
          v=w;
          w=u;
          fv=fw;
          fw=fu;
        } else if (fu <= fv || v == x || v == w) {
          v=u;
          fv=fu;
        }
      }  // done with housekeeping.  Back for another iteration
    } // end of main loop.

    setStatusString("Too many iterations in brent line search");
    xmin=x;
    newWeights.addScaled(weights,xmin,direction);
    return false;
  }