[ return ]

gate.c



/*
 * file: gate.c
 *
 * [DEFINE DESCRIPTION = Gate class (part of the column object)]
 *
 *  Name                Date        Description
 *  --------------      --------    -------------------------------------
 *  Andrew H. Fagg      09/05/93    Original
 *
 *
 *
 *
 *
 *
 */

#include "nsl_include.h"
#include "gate.h"
#include "alib.h"
#include "gen.h"

/* #define DEBUG */
/*#define DEBUG2 */

/*
  * gate_class::gate_class(char* local_name, name_class* parent,
  *	                   short weight_flags, gate_parms_class* pparms)
  *
  *    Create a gate type: initialize name, connectors, and parms.
  *
  */

gate_class::gate_class(char* local_name, name_class* parent,
		       short weight_flags, gate_parms_class* pparms)
{
  name = new name_class(local_name, parent);

#ifdef DEBUG
  cout << "*** gate_class::gate_class() :" << name << " ***" nl;
#endif 

				/* Create connectors. */
  priming_connector = new connector_class(weight_flags);
  support_connector = new connector_class(weight_flags);

				/* NULL weight vectors for now. */
  priming_weights = NULL;
  support_weights = NULL;

				/* Parameters. */
  parms = pparms;
}



/*
 *  gate_class::~gate_class()
 *
 *  Gate class destructor : delete allocated vars.
 */

gate_class::~gate_class()
{
  delete priming_connector;
  delete support_connector;
  if(priming_weights != NULL)
      delete priming_weights;
  if(support_weights != NULL)
    delete support_weights;
  delete name;
}

/*
  * void gate_class::init_weights()        //OVERLOAD CALL: init_weights: column.c(column_class), gate.c(gate_class), layer.c(layer_class)
  *
  *  Intialize the weight vectors.  First create, and then set
  * the vectors to the initial values stored in the connectors.
  *
  */

void gate_class::init_weights()
{
#ifdef DEBUG
  cout << "*** Init weights for " << name << " ***" nl;
#endif

  int weight_size;

				/* Priming connector */
				/* How big is vector? */
  weight_size = priming_connector->get_num_connections();        //OVERLOAD CALL: get_num_connections: connector.c(connector_class), reverse_connector.c(reverse_connector_input_class), reverse_connector.c(reverse_connector_output_class)
  if(weight_size != 0)
    {
				/* Create weight vector */
      priming_weights = new nsl_vector(weight_size);
				/* Get initial values. */
      *priming_weights = priming_connector->get_initial_weights(0,0,0);
    }
				/* Support connector */
				/* How big is vector? */
  weight_size = support_connector->get_num_connections();        //OVERLOAD CALL: get_num_connections: connector.c(connector_class), reverse_connector.c(reverse_connector_input_class), reverse_connector.c(reverse_connector_output_class)
  if(weight_size != 0)
    {
				/* Create weight vector */
      support_weights = new nsl_vector(weight_size);
				/* Get initial values. */
      *support_weights = support_connector->get_initial_weights(0,0,0);
    }
}


/*
  * void gate_class::clear_activities()        //OVERLOAD CALL: clear_activities: column.c(column_class), gate.c(gate_class), layer.c(layer_class)
  *
  *  Clear the activity levels of the priming and support units.
  *
  */

void gate_class::clear_activities()
{
#ifdef DEBUG
  cout << "*** gate_class::clear_activities() : " << name << " ***" nl;        //OVERLOAD CALL: clear_activities: column.c(column_class), gate.c(gate_class), layer.c(layer_class)
#endif
  prime_mem = 0;
  prime = 0;
  support_mem = 0;
  support = 0;

  pet_pos = 0;
  pet_neg = 0;
}


/*
  * void gate_class:forward()
  *
  *  Update the activity levels of the priming and support units.
  *
  */

void gate_class::forward()
{

#ifdef DEBUG
  cout << "*** gate_class:forward() " << name << " ***" nl;
#endif

  pet_pos = 0;
  pet_neg = 0;
				/* Priming unit membrane potential. */
  if(priming_connector->get_num_connections() > 0)        //OVERLOAD CALL: get_num_connections: connector.c(connector_class), reverse_connector.c(reverse_connector_input_class), reverse_connector.c(reverse_connector_output_class)
    {
      prime_mem = (*priming_weights
		   ^ priming_connector->get_values()).sum();        //OVERLOAD CALL: get_values: connector.c(connector_class), reverse_connector.c(reverse_connector_input_class), reverse_connector.c(reverse_connector_output_class), sensor.c(sensor_class)

				/* Compute synaptic activity */
      if(parms->pet_flag->elem() == 1.0)
	{
	  pet_pos = pet_pos + NSLramp(*priming_weights
		   ^ priming_connector->get_values()).sum();        //OVERLOAD CALL: get_values: connector.c(connector_class), reverse_connector.c(reverse_connector_input_class), reverse_connector.c(reverse_connector_output_class), sensor.c(sensor_class)
	  pet_neg = pet_neg + NSLramp(- *priming_weights
		   ^ priming_connector->get_values()).sum();        //OVERLOAD CALL: get_values: connector.c(connector_class), reverse_connector.c(reverse_connector_input_class), reverse_connector.c(reverse_connector_output_class), sensor.c(sensor_class)
	};
    }
  else				/* No inputs */
    prime_mem = 0;

				/* Activity level */
  prime = NSLsat(prime_mem, parms->pr_kx1->elem(),
		            parms->pr_kx2->elem(),
			    parms->pr_ky1->elem(),
			    parms->pr_ky2->elem());

				/* Support unit membrane potential. */
  if(support_connector->get_num_connections() > 0)        //OVERLOAD CALL: get_num_connections: connector.c(connector_class), reverse_connector.c(reverse_connector_input_class), reverse_connector.c(reverse_connector_output_class)
    {
      support_mem = (*support_weights ^ support_connector->get_values()).sum()        //OVERLOAD CALL: get_values: connector.c(connector_class), reverse_connector.c(reverse_connector_input_class), reverse_connector.c(reverse_connector_output_class), sensor.c(sensor_class)
	+ prime - threshold;

				/* Compute synaptic activity */
      if(parms->pet_flag->elem() == 1.0)
	{
	  pet_pos = pet_pos + NSLramp(*support_weights ^
			    support_connector->get_values()).sum();        //OVERLOAD CALL: get_values: connector.c(connector_class), reverse_connector.c(reverse_connector_input_class), reverse_connector.c(reverse_connector_output_class), sensor.c(sensor_class)
	  pet_neg = pet_neg + NSLramp(- *support_weights ^
			    support_connector->get_values()).sum();        //OVERLOAD CALL: get_values: connector.c(connector_class), reverse_connector.c(reverse_connector_input_class), reverse_connector.c(reverse_connector_output_class), sensor.c(sensor_class)
	};
    }
  else				/* No inputs */
    support_mem = prime - threshold;
  
				/* Activity level */
  support = NSLramp(support_mem, parms->support_kx1->elem(),
			    parms->support_ky1->elem(),
			    parms->support_ky2->elem());
}

/*
 * name_class* gate_class::get_name()        //OVERLOAD CALL: get_name: column.c(column_class), connector.c(connector_class), gate.c(gate_class), layer.c(layer_class), reverse_connector.c(reverse_connector_input_class), reverse_connector.c(reverse_connector_output_class), sensor.c(sensor_class)
 *
 *  Return the gate name.
 */

name_class* gate_class::get_name()
{
  return name;
}



/*
 * nsl_data* gate_class::get_prime()
 *
 * Return a pointer to the activation level of the gate.
 *
 */

nsl_data* gate_class::get_prime()
{
  return ′
}

/*
 * nsl_data* gate_class::get_prime_mem()
 *
 *  Return a pointer to the membrane potential level of the gate.
 *
 */

nsl_data* gate_class::get_prime_mem()
{
  return &prime_mem;
}


/*
 * nsl_data* gate_class::get_support()
 *
 * Return a pointer to the activation level of the gate.
 *
 */

nsl_data* gate_class::get_support()
{
  return &support;
}

/*
 * nsl_data* gate_class::get_support_mem()
 *
 *  Return a pointer to the membrane potential level of the gate.
 *
 */

nsl_data* gate_class::get_support_mem()
{
  return &support_mem;
}


/*
 * nsl_vector* gate_class::get_priming_weights()
 *
 * Return a pointer to the priming weight vector.
 *
 */

nsl_vector* gate_class::get_priming_weights()
{
  return priming_weights;
}

/*
 * nsl_vector* gate_class::get_support_weights()
 *
 * Return a pointer to the support weight vector.
 *
 */

nsl_vector* gate_class::get_support_weights()
{
  return support_weights;
}



/*
 * nsl_vector* gate_class::get_priming_inputs()
 *
 *  Return a pointer to the current priming inputs into the gate.
 *
 */
/*
nsl_vector* gate_class::get_priming_inputs()
{
  return priming_connector->get_values();        //OVERLOAD CALL: get_values: connector.c(connector_class), reverse_connector.c(reverse_connector_input_class), reverse_connector.c(reverse_connector_output_class), sensor.c(sensor_class)
}
*/

/*
 * nsl_vector* gate_class::get_support_inputs()
 *
 *  Return a pointer to the current support inputs into the gate.
 *
 */
/*
nsl_vector* gate_class::get_support_inputs()
{
  return support_connector->get_values();        //OVERLOAD CALL: get_values: connector.c(connector_class), reverse_connector.c(reverse_connector_input_class), reverse_connector.c(reverse_connector_output_class), sensor.c(sensor_class)
}
*/


/*
 * connector_class* gate_class::get_priming_connector()
 *
 *  Return a pointer to the gate priming connector.
 *
 */

connector_class* gate_class::get_priming_connector()
{
  return priming_connector;
}


/*
 * connector_class* gate_class::get_support_connector()
 *
 *  Return a pointer to the gate support connector.
 *
 */

connector_class* gate_class::get_support_connector()
{
  return support_connector;
}


/*
  * connector_class* gate_class::get_connector(int unit)
  *
  *  Return the specified connector
  *
  */

connector_class* gate_class::get_connector(int unit)
{
 switch(unit)
   {
   case SUPPORT:
     return support_connector;
   case PRIME:
     return priming_connector;
   default:
     cout << "gate_class::get_connector(): " << name <<
       "Error - illegal unit specified." nl;
     return NULL;
   }
}

/*
 * void gate_class::report_gate(int connector_flag)        //OVERLOAD CALL: report_gate: column.c(column_class), gate.c(gate_class), layer.c(layer_class)
 *
 *  Print out all unit state information.
 *
 */

void gate_class::report_gate(int connector_flag)
{


  cout << "--------------------------" nl;
  cout << "Unit: " << name nl;
  cout << "prime mem = \t" << prime_mem;
  cout << "prime act = \t" << prime;
  cout << "support mem = \t" << support_mem;
  cout << "support act = \t" << support;
  cout << "threshold = \t" << threshold;
  cout nl;
  if(connector_flag)
    {
      cout << "Priming Connector" nl;
      if(priming_connector->get_num_connections())        //OVERLOAD CALL: get_num_connections: connector.c(connector_class), reverse_connector.c(reverse_connector_input_class), reverse_connector.c(reverse_connector_output_class)
	{
	  nsl_vector tmp = priming_connector->get_values();        //OVERLOAD CALL: get_values: connector.c(connector_class), reverse_connector.c(reverse_connector_input_class), reverse_connector.c(reverse_connector_output_class), sensor.c(sensor_class)
	  priming_connector->report_state(priming_weights, &tmp, NULL, NULL);        //OVERLOAD CALL: report_state: connector.c(connector_class), reverse_connector.c(reverse_connector_input_class), reverse_connector.c(reverse_connector_output_class)
	}
      else
	cout << "Empty" nl;

      cout << "Support Connector" nl;
      if(support_connector->get_num_connections())        //OVERLOAD CALL: get_num_connections: connector.c(connector_class), reverse_connector.c(reverse_connector_input_class), reverse_connector.c(reverse_connector_output_class)
	{
	  nsl_vector tmp2 = support_connector->get_values();        //OVERLOAD CALL: get_values: connector.c(connector_class), reverse_connector.c(reverse_connector_input_class), reverse_connector.c(reverse_connector_output_class), sensor.c(sensor_class)
	  support_connector->report_state(support_weights, &tmp2, NULL, NULL);        //OVERLOAD CALL: report_state: connector.c(connector_class), reverse_connector.c(reverse_connector_input_class), reverse_connector.c(reverse_connector_output_class)
	}
      else
	cout << "Empty" nl;

      cout nl;
    }
}


int gate_class::stuff(ifstream& netfile)
{
  float val;
  char tmp[STRSIZE];

#ifdef DEBUG2
  cout << "Stuffing gate " << name nl;
#endif

  netfile >> val;		/* Get the threshold */
  threshold = val;

  netfile >> tmp;		/* priming connector header: 'priming' */
  if(strncmp(tmp, "priming", STRSIZE))
    {
      cout << "Stuffing gate " << name << ", expected priming, but got:" nl;
      cout << tmp nl;
      return 0;
    }
  netfile >> tmp;		/* Get 'connector' */
  if(strncmp(tmp, "connector", STRSIZE))
    {
      cout << "Stuffing gate (priming) " << name << ", expected connector, but got:" nl;
      cout << tmp nl;
      return 0;
    }
				/* Get the connector */
  if(!priming_connector->stuff(netfile))        //OVERLOAD CALL: stuff: gate.c(gate_class), layer.c(layer_class), column.c(column_class), connector.c(connector_class)
    return 0;


      
  netfile >> tmp;		/* support connector header: 'support' */
  if(strncmp(tmp, "support", STRSIZE))
    {
      cout << "Stuffing gate " << name << ", expected support, but got:" nl;
      cout << tmp nl;
      return 0;
    }
  netfile >> tmp;		/* Get 'connector' */
  if(strncmp(tmp, "connector", STRSIZE))
    {
      cout << "Stuffing gate (support) " << name << ", expected connector, but got:" nl;
      cout << tmp nl;
      return 0;
    }
				/* Get the connector */
  if(!support_connector->stuff(netfile))        //OVERLOAD CALL: stuff: gate.c(gate_class), layer.c(layer_class), column.c(column_class), connector.c(connector_class)
    return 0;
      
  return 1;
};

/*
  * float gate_class::get_pet_pos()        //OVERLOAD CALL: get_pet_pos: column.c(column_class), gate.c(gate_class)
  *
  *  Return the positive contribution to the pet measure.
  *
  */

float gate_class::get_pet_pos()
{
  return(pet_pos.elem());
};

/*
  * float gate_class::get_pet_neg()        //OVERLOAD CALL: get_pet_neg: column.c(column_class), gate.c(gate_class)
  *
  *  Return the negative contribution to the pet measure.
  *
  */

float gate_class::get_pet_neg()
{
  return(pet_neg.elem());
};


[ return ]