⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 bfagent.m

📁 人工智能的matlab程序
💻 M
📖 第 1 页 / 共 5 页
字号:
   index=[ fcastList begin: [self getZone]];
    for ( aForecast=[index next]; [index getLoc]==Member; aForecast=[index next] )
    {
       if ( [aForecast getConditionsWord: 0] & [worldvalues getConditionsWord: 0] ) continue ;
       if ( [aForecast getConditionsWord: 1] & [worldvalues getConditionsWord: 1] ) continue ;
       [activeList addLast: aForecast];
    }
    [index drop];

      break;
   
 case 3:
    
  index=[ fcastList begin: [self getZone]];
    for ( aForecast=[index next]; [index getLoc]==Member; aForecast=[index next] )
    {
       if ( [aForecast getConditionsWord: 0] & [worldvalues getConditionsWord: 0] ) continue ;
       if ( [aForecast getConditionsWord: 1] & [worldvalues getConditionsWord: 1] ) continue ;
       if ( [aForecast getConditionsWord: 2] & [worldvalues getConditionsWord: 2] ) continue ;
       [activeList addLast: aForecast];
    }
    [index drop];
     break;
    case 4:
 
    index=[ fcastList begin: [self getZone]];
    for ( aForecast=[index next]; [index getLoc]==Member; aForecast=[index next] )
    {
      if ( [aForecast getConditionsWord: 0] & [worldvalues getConditionsWord: 0]) continue ;
      if ( [aForecast getConditionsWord: 1] &  [worldvalues getConditionsWord: 1] ) continue ;
      if ( [aForecast getConditionsWord: 2] &  [worldvalues getConditionsWord: 2] ) continue ;
      if ( [aForecast getConditionsWord: 3] &  [worldvalues getConditionsWord: 3] ) continue ;
       [activeList addLast: aForecast];
    }
    [index drop];

      break;
    case 5:
 
    index=[ fcastList begin: [self getZone]];
    for ( aForecast=[index next]; [index getLoc]==Member; aForecast=[index next] )
    {
       if ( [aForecast getConditionsWord: 0] & [worldvalues getConditionsWord: 0] ) continue ;
       if ( [aForecast getConditionsWord: 1] & [worldvalues getConditionsWord: 1] ) continue ;
       if ( [aForecast getConditionsWord: 2] & [worldvalues getConditionsWord: 2] ) continue ;
       if ( [aForecast getConditionsWord: 3] & [worldvalues getConditionsWord: 3] ) continue ;
       if ( [aForecast getConditionsWord: 4] & [worldvalues getConditionsWord: 4] ) continue ;
       [activeList addLast: aForecast];
    }
    [index drop];
      break;
        }

#if MAXCONDBITS > 5*16
#error Too many condition bits (MAXCONDBITS)
#endif

  
   //pj??? There ought to be a "default" action here for other cases.


  /*This is an alternative implementation of the same as preceeding.
It is so much cuter in my view.  I wrote it before I understood the
fact that the World gives back 10 for yes and agent has 01 for yes, so
you have to be careful with it. Note the bitmath here, that appears
as it used to throughout the BFagent class.
  
    index=[ fcastList begin: [self getZone]];
    for ( aForecast=[index next]; [index getLoc]==Member; aForecast=[index next] )
    {
      unsigned int flag=0;
      unsigned int trit;
      unsigned int predictedvalue=999;
     
      trit=-1;
      while ( flag == 0 && ++trit < privateParams-> condbits )
	    {
	      if ( (predictedvalue=[aForecast getConditionsbit: trit]) != 0 )
		{
		  //if ( predictedvalue == ((worldvalues[WORD(trit)] >> ((trit%16)*2))&3) )
		  if (  predictedvalue == [worldvalues getConditionsbit: trit] )
		    {
		      flag=1;
		    }
		}
	        		
	   //       fprintf(stderr,"trit:%d flag: %d  predictionl=%d,  world=%d\n", 
	      //  			trit, flag, predictedvalue,
	      //  			extractvalue(worldvalues,trit) );  
	         }
     
	    if ( flag!=1 )  [activeList addLast: aForecast];
    
        }
    [index drop]; */

  return self;
}

/*"Currently does nothing, used only if their are ANNagents"*/
- getInputValues     
{
  return self;
}

/*"Currently does nothing, used only if their are ANNagents"*/
- feedForward        
{
  return self;
}


- (double)getDemandAndSlope: (double *)slope forPrice: (double)trialprice
  /*" Returns the agent's requested bid (if >0) or offer (if <0) using
* best (or mean) linear forecast chosen by -prepareForTrading. The
* forecast is given by 

   forecast = pdcoeff*(trialprice+dividend) + offset 

* where pdcoeff and offset are set by -prepareForTrading.

A risk aversion computation gives a target holding, and its
derivative ("slope") with respect to price.  The slope is calculated
as the linear approximated response of a change in price on the
traders' demand at time t, based on the change in the forecast
according to the currently active linear rule. "*/

{
  forecast = (trialprice + dividend)*pdcoeff + offset;


  if (forecast >= 0.0) 
    {
      demand = -((trialprice*intratep1 - forecast)/divisor + position);
      *slope = (pdcoeff-intratep1)/divisor;
    }
  else 
    {
      forecast = 0.0;
      demand = - (trialprice*intratep1/divisor + position);
      *slope = -intratep1/divisor;
    }

  // Clip bid or offer at "maxbid".  This is done to avoid problems when
  // the variance of the forecast becomes very small, thought it's not clear
  // that this is the best solution.
  if (demand > privateParams->maxbid) 
    { 
      demand = privateParams->maxbid;
      *slope = 0.0;
    }
  else if (demand < -privateParams->maxbid) 
    {
      demand = -privateParams->maxbid;
      *slope = 0.0;
    }
    
  [super constrainDemand:slope:trialprice];
  return demand;
}


/*"Return agent's forecast"*/
- (double)getRealForecast
{
  return forecast;
}


/*" Now update the variance and strength of all the forecasts that
  were active in the previous period, since now we know how they
  performed. This method causes an update of price/dividend
  information from the world, then it measures how far off each
  forecast was and puts the square of that "deviance" measure into the
  forecast with the forecast's setVariance: method. Each forecast in
  the active list is told to update its forecast.  It also updates the
  instance variable variance, which is calculated here as an
  exponentially weignted moving average of that forecast's
  squared-error (variance).  Inside the code of updatePerformance,
  there is a description of the strength formula that is used, and how
  the formula now matches the formula used in the original sfsm,
  rather than ASM-2.0. "*/

- updatePerformance
{
  //pj: register struct BF_fcast *fptr;
  BFCast *  aForecast;
  id <Index> index = nil;
  double deviation, ftarget, tauv, a, b, c, av, bv, maxdev;

  // Precompute things for speed
  tauv = privateParams->tauv;
  a = 1.0/tauv;
  b = 1.0-a;
  // special rates for variance
  // We often want this to be different from tauv
  // PARAM:  100. should be a parameter  BL
  av = 1.0/(double)100.0;
  bv = 1.0-av;

    /* fixed variance if tauv at max */
  if (tauv == 100000) 
    {
      a = 0.0;
      b = 1.0;
      av = 0.0;
      bv = 1.0;
    }
  maxdev = privateParams->maxdev;

// Update global mean (p+d) and our variance
  [self getPriceFromWorld];
  ftarget = price + dividend;

// Update global mean (p+d) and our variance
    
  realDeviation = deviation = ftarget - lforecast;
  if (fabs(deviation) > maxdev) deviation = maxdev;
  global_mean = b*global_mean + a*ftarget;
  // Use default for initial variances - for stability at startup
  currentTime = getCurrentTime( );
  if (currentTime < 1)
    variance = privateParams->initvar;
  else
    variance = bv*variance + av*deviation*deviation;

 //I cant find anywhere in ASM-2.0's BFagent.m an update of the forecast's
 //forecast. but it is clearly needed if you look at bfagent from the
 //objc version. Including the next loop
 //fixes the strange time series properties too
 
  //printf("active list has %d \n",[activeList getCount] );

  index = [ activeList begin: [self getZone]];
  for( aForecast=[index next]; [index getLoc]==Member; aForecast=[index next] )
    {
      [aForecast updateForecastPrice: price Dividend: dividend];
    }
  [index drop];
   
  //pj: Here is the way it was
// Update all the forecasters that were activated.
//    if (currentTime > 0)
//      for (fptr=lactivelist; fptr!=NULL; fptr=fptr->lnext) 
//        {
//          deviation = (ftarget - fptr->lforecast)*(ftarget - fptr->lforecast);

//  // 	Benchmark test line - replace true deviation with random one
//  //      PARAM: Might be coded as a parameter sometime 
//  //      deviation = drand(); 

//  //      Only necessary for absolute deviations
//  //      if (deviation < 0.0) deviation = -deviation;

//  	if (deviation > maxdev) deviation = maxdev;
//    	if (fptr->count > tauv)
//  	  fptr->variance = b*fptr->variance + a*deviation;
//  	else 
//  	  {
//  	    c = 1.0/(1.+fptr->count);
//  	    fptr->variance = (1.0 - c)*fptr->variance +
//  						c*deviation;
//  	  }
//          fptr->strength = fptr->specfactor/fptr->variance;
//        }

  if (currentTime > 0)
    {
      index = [ oldActiveList begin: [self getZone]];
      for( aForecast=[index next]; [index getLoc]==Member; aForecast=[index next] )
	{
	  double  lastForecast=[aForecast getLforecast];
	  deviation = (ftarget - lastForecast)*(ftarget - lastForecast);

	  if (deviation > maxdev) deviation = maxdev;
	  if ([aForecast getCnt] > tauv)
	    [aForecast setVariance : b*[aForecast getVariance] + a*deviation];
	  else 
	    {
	      c = 1.0/(double) (1.0 +[aForecast getCnt]);  //??bfagent had no 1+ here ??
	      [aForecast setVariance: (1.0 - c)*[aForecast getVariance] +
			 c*deviation];
	    }
	  
	  [aForecast setStrength: privateParams->maxdev 
		     - [aForecast getVariance]
		     + [aForecast getSpecfactor]];
	  // ****************************************/
	  // pj: The preceeding is based on sfsm's bfagent.m
	  // 
	  // original bfagent has this: rptr->strength = p->maxdev -
	  // rptr->variance + rptr->specfactor; 

	  // BFagent in ASM-2.0 had this: fptr->strength =
	  // fptr->specfactor/fptr->variance; I've spoken to Blake
	  // LeBaron and we both like the old way and don't know why it
	  // was changed. 

	  // I hasten to say that maxdev is the benchmark for
	  // variance, and I wonder if maxdev would not be better
	  // renamed maxdev-squared or maxvar.
	  //******************************************/
	}

      [index drop];
    }
 
  return self;
}

/*"Returns the absolute value of realDeviation"*/
- (double)getDeviation
{
  return fabs(realDeviation);
}

/*"Currently, does nothing, used only if their are ANNagents"*/
- updateWeights        
{
  return self;
}


/*"Returns the "condbits" variable from parameters: the number of
  condition bits that are monitored in the world, or 0 if
  condition bits aren't used.
  "*/
- (int)nbits
{
  return privateParams->condbits;
}

/*"Returns the number of forecasts that are used. In the original
  design, this was a constant set in the parameters, although revision
  of the code for ASM-2.2 conceivably should allow agents to alter the
  number of forecasts they maintain."*/
- (int)nrules
{
  return privateParams->numfcasts;
}

/*"Return the last time the Genetic Algorithm was run.
//	Agents that don't use a genetic algorithm return MININT.  This
//	may be used to see if the bit distribution might have changed,
//	since a change can only occur through a genetic algorithm."*/
- (int)lastgatime
{
  return lastgatime;
}


/*"Currently, this method is not called anywhere in ASM-2.2. It might
  serve some purpose, past or present, I don't know (pj:
  2001-11-26)"*/
//   Original docs from ASM-2.0
//	Places in (*countptr)[0] -- (*countptr)[3] the addresses of 4
//	arrays, (*countptr)[0][i] -- (*countptr)[3][i], which are filled
//	with the number of bits that are 00, 01, 10, or 11 respectively,
//	for each condition bit i= 0, 1, nbits-1, summed over all rules or
//	forecasters.  Returns nbits, the number of condition bits.  If
//	cum is YES, adds the new counts to whatever is in the (*coutptr)
//	arrays already.  Agents that don't use condition bits return -1.
//	The 4-element array (*countptr)[4] must already exist, but the
//	arrays to which its element point are supplied dynamically.  This
//	method must be provided by each subclass that has condition bits.
- (int)bitDistribution: (int *(*)[4])countptr cumulative: (BOOL)cum
{
  BFCast * aForecast;
  unsigned int *agntcond;
  int i;
  int condbits;
  id index;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -