text: // Na Ion Channel Dynamics (Baker 2003)
  //
  // Copyright 2007 John L Baker. All rights reserved.
  //
  // This software is provided AS IS under the terms of the Open Source
  // MIT License. See http://www.opensource.org/licenses/mit-license.php.
  //
  // File: ionchan_na_baker_2003.h
  //
  // Release:		1.0.0
  // Author:		John Baker
  // Updated:		14 July 2006
  //
  // Description:
  //
  // This header file contains the classes used to implement
  // the sodium (Na) channel based primarily on data from the Gasparini and Magee
  // 2002 article for dendritic channels and Pan and Colbert for soma and axon.
  // Persistent Na currents are better characterized in EC neurons and the
  // voltage dependency there is used here for CA3 (see below).
  //
  // Pan & Colbert found that half of the Na current was not inactivated at
  // +20mV relative to rest (i.e. at approx -50mV). To allow for this and to
  // support slow inactivation, a special s gate is added to the usual model.
  // The h gate is voltage shifted so that its vhalf is approximately -50mV
  // and the combination of h*s gates is the steady-state inactivation voltage 
  // response measured by Gasparini & Magee for dendrites and Colbert & Pan
  // for soma. No s gate is used for axon channels.
  //
  // In EC, persistent sodium currents occur in bursts which have time
  // constants largely independent of voltage (see Magistretti and Alonso). 
  // No attempt is made here to model these kinetics because experimental 
  // data is not sufficient to do so. Slow inactivation is included primarily
  // to make resting voltage more stable. French extrapolates the I-V 
  // relationship to give a reversal potential of +8mV for this current,
  // but a reversal potential from Magistretti and Alonso is used instead.
  //
  // Q10 values may be inaccurate. Activation gate Q10 is chosen as typical
  // of activation gates. Note that the minimum tau value is not affected by
  // temperature. For inactivation, Sah et al. show a difference in Na current 
  // decay times at different temperatures. Values used here are at best rough 
  // estimates and are chosen as a compromise with the inactivation time constant 
  // found by Pan & Colbert (37 msec at -50mV) for 32 deg C with that found by 
  // Costa at 22 deg C. Because of the relationship between activation and 
  // inactivation processes, inactivation at depolatized potentials may be less
  // sensitive to temperature. Differences in slow inactivation as measured by
  // Mikus et al. and by Colbert et al. could be due to temperature, in which
  // case a Q10 of 2-3 would be appropriate. 
  //
  // References:
  //
  // Colbert CM, Magee JC, Hoffman DA, Johnston D (1997). Slow recovery from
  // inactivation of Na+ channels underlies the activity-dependent attentuation
  // of dendritic action potentials in hippocampal CA1 pyramidal neurons.
  // J Neurosci. 17, 6512-6521
  // 
  // Colbert CM and Pan E (2002). Ion channel properties underlying axonal action 
  // potential initiation in pyramidal neurons. Nature Neuroscience 5, 533-538.
  //
  // Costa PF, 1996. The kinetic parameters of sodium currents in maturing
  // acutely isolated rat hippocampal CA1 neurones. 
  // Developmental Brain Research 91,29-40.
  //
  // French CR, Sah P, Buckett KJ, and Gage PW (1990). A voltage-dependent
  // persistent sodium current in mammalian hippocampal neurons.
  // J. Gen Physiol. 95(6), 1139-1157.
  //
  // Gasaprini S and Magee JC, 2002. Phosphorylation-dependent differences
  // in the activation properties of distal and proximal dendritic Na+
  // channels in rat CA1 hippocampal neurons. J. Physiology 541.3, 665-672.
  //
  // Hu H, Vervaeke K, and Storm J. (2002). Two forms of electrical 
  // resonance at theta frequencies, generated by M-current, h-current
  // and persistent Na+ current in rat hippocampal pyramidal cells.
  // J. Physiology 545, 783-805.
  //
  // Magee JC, Johnston D (1995). Characterization of single
  // voltage-gated Na+ and Ca++ channels in apical dendrites
  // of rat CA1 pyramidal neurons. J. Physiology 487, 67-90.
  //
  // Magistretti J and Alonso A (1999). Biophysical properties of slow
  // voltage-dependent inactivation of a sustained sodium current in
  // entorhinal cortex layer II principal cells. 
  // J. Gen. Physiol. 114, 491-509.
  //
  // Magistretti J and Alonso A (2002). Fine gating properties of channels
  // responsible for persistent sodium current generation in entorhinal cortex
  // neurons. J. Gen. Physiol. 120, 855-873.
  //
  // Mikus T, Jung H, and Spruston N (1999). Properties of slow, cumulative
  // sodium channel inactivation in rat hippocampal CA1 pyramidal neurons.
  // Biophysical Journal 76, 846-860.
  //
  // Pan E and Colbert CM, 2001. Subthreshold inactivation of Na+ and
  // K+ channels supports activity-dependent enhancement of back-propagating
  // action potentials in hippocampal CA1. J. Neurophysiology 85, 1013-1016.
  //
  // Sah P, Gibb AJ, and Gage PW, 1988. The sodium current underlying action
  // potentials in guinea pig hippocampal CA1 neurons. 
  // J. Gen. Physiol. 91, 373-398.
  //
  // Tsubokawa H and Ross WN (1997). Muscarinic modulation of spike back-
  // propagation in the apical dendrites of hippocampal CA1 pyramidal neurons.
  // J Neurosci. 17, 5782-5791. 
  
  
  // Only include this header once
  #ifndef __IONCHAN_NA_BAKER_2003_H_
  #define __IONCHAN_NA_BAKER_2003_H_
  
  #include "bnsf.h"
  
  using namespace std;
  using namespace BNSF;
  
  namespace BAKER_2003 {
  
  	// ================================================================
  	// Common superclasses used in building Na channel objects
  	// ================================================================
  
  	// Abstract Na h gate ---------------------------------------------
  
  	// Gate properties take into account state transition open->inact
  	// in which channel inactivation is dependent on open state value.
  	// Voltage sensitivity is a combination of a single energy barrier
  	// with adjustments for dependency on the activation (m) gate.
  
  	// The activation gate must be an order 3 gate, that is activation
  	// open probability is m*m*m. alpha() and beta() functions only return the
  	// energy barrier component as does printAlphaBetaTable.
  
  	// Parameters for the energy barrier component are provided in subclasses.
  
  	class Abstract_Na_h_gate : public EnergyBarrierTabGate {
  
  	public:
  
  		// Constructors and destructor
  		Abstract_Na_h_gate(IonChannel* mgate=NULL);
  		virtual ~Abstract_Na_h_gate();
  
  		// Accessors for activation gate
  		inline  IonChannel*			mgate()					{ return _mgate; }
  		virtual void				mgate(IonChannel* mg)	{ _mgate=mg; }
  
  		// Establish dependency on mgate to ensure consistent evaluation order
  		virtual bool				hasPrequisites() { return true; }
  		virtual ModelComponent*		prerequisite() { return mgate(); }
  		
  		// Fastpath computation of derivatives
  		// including effects of activation gate.
  		virtual void				computeDerivatives();
  
  		// Fastpath computation of local state update
  		// including effects of activation gate.
  		virtual bool				canPerformLocalUpdate() { return true; }
  		virtual void				localStateUpdate(SimTime h, CNStepType stepType);
  
  		// Save parameter values for fast path on simulation started
  		virtual void				simulationStarted();
  
  		// State vector label functions
  		virtual const char*	componentName() {return "Na"; }
  		virtual const char** stateLabels() {
  			static const char* sl[] = { "h" }; return sl; }
  
  		// Subclass responsiblities ----------------------------
  
  		// Specify parameter for rate of additional open->inact transitions
  		virtual Number				inactRate() = 0;
  
  		// Specify parameter for additional value added to computed tau.
  		// This functions like tauMin but is after the energy barrier component
  		// and m-gate dependent component are combined.
  		virtual Number				tauZero() = 0;
  
  	protected:
  		IonChannel*					_mgate;
  		Number						_inactRate;
  		Number						_tauZero;
  	};
  
  	// Na h gate ------------------------------------------
  
  	// This gate provides fast inactivation for the Na channel.
  	// It is intended to be used with a matching s gate and the
  	// product of the two is Na channel inactivation.
  
  	class Na_h_gate : public Abstract_Na_h_gate {
  
  	public:
  		// Constructors and destructor
  		Na_h_gate(IonChannel* mgate=NULL) : Abstract_Na_h_gate(mgate) {}
  		virtual ~Na_h_gate() {}
  
  		// Temperature dependency (see notes above).
  		virtual Number	ratedTempC()	{return  22; }
  		virtual Number	Q10()			{return  2; }
  
  		// Voltage dependency from Gasparini & Magee adjusted to work
  		// with an s gate. The slope is adjusted to take into account 
  		// the effect of m-gate state on inactivation.
  		virtual Number	Vhalf()			{return -50*UOM::mV; }
  		virtual Number	slope()			{return -8*UOM::mV; }
  		
  		// Time constants. There is something of a conflict between
  		// values from Costa (whole cell) and those of Pan & Colbert
  		// (in dendrite) because different temperatures are used.
  		// These values attempt to split the difference. There is also a
  		// suggestion in later work by Colbert et al. (SFN2003 poster)
  		// that the 37 msec value may be high.
  		virtual Number	tauMax()		{return  45*UOM::msec; }
  		virtual Number	gamma()			{return  0.2f; }
  
  		// Specify parameter for rate of additional open->inact transitions.
  		virtual Number	inactRate()		{ return 1.5/UOM::msec; }
  
  		// Specify parameter for additional value added to computed tau.
  		// This functions is like tauMin but is after the energy barrier 
  		// component and m-gate dependent component are combined.
  		virtual Number	tauZero()		{return  0.4*UOM::msec; }
  
  		// Because this gate uses the current value of the m gate,
  		// it may not be second order accurate in time.
  		virtual bool	isSecondOrderAccurate() { return false; }
  
  	protected:
  		virtual AlphaBetaEntry**	pAlphaBetaTable() { return &_abTable; }
  
  	private:
  		static AlphaBetaEntry*		_abTable;
  	};
  	
  	// Abstract Na s gate --------------------------------------------
  
  	// This gate controls slow activation. The gate is adjusted to result
  	// such that a combination of h*s is the steady state inactivation
  	// measured. Subclasses extend by supplying parameters.
  
  	class Abstract_Na_s_gate : public EnergyBarrierTabGate {
  
  	public:
  		// Constructors and destructor
  		Abstract_Na_s_gate(
  			bool isDisabled=false,	// set gateDisabled on or off
  			Number dval=0.5f);		// set default disabled value
  
  		virtual ~Abstract_Na_s_gate();
  
  		// Temperature dependency
  		virtual Number	ratedTempC()	{return  37; }
  		virtual Number	Q10()			{return	 1; }
  
  		// Allow for difference between h and s gate Vhalf values.
  		// To have h*s be an ideal sigmoidal curve we would set this
  		// to be exp(dV/k) where dV is the different in Vhalf values
  		// and k the common slope variable. The value here is exp(-17/8).
  		virtual Number	xinfAbsMin()	{return 0.12f; }
  
  		// Access a switch that turns gate on or off. If off, the gate always
  		// returns the gate disable value regardless of voltage.
  		inline  bool	gateDisabled()	{return _gateDisabled; }
  		virtual void	gateDisabled(bool flag) { _gateDisabled = flag; }
  
  		// Access the static value used when the gate is off.
  		inline	Number	disabledValue() {return _disabledValue; }
  		virtual void	disabledValue(Number s) { _disabledValue = s; }
  
  		// Access the static time constant when the gate is off
  		inline  Number	disabledTau() {return _disabledTau; }
  		virtual void	disabledTau(Number tau) { _disabledTau = tau; }
  
  		// Special interfaces to be overridden when gate is disabled
  		virtual void	computeDerivatives();
  		virtual void	localStateUpdate(SimTime h, CNStepType stepType);
  
  		// Provide accessors for Hodgkin-Huxley rate values
  		// adjusted for gate status as needed.
  		virtual Number	alpha();
  		virtual Number	beta();
  
  		// State vector label functions
  		virtual const char*	componentName() {return "Na"; }
  		virtual const char** stateLabels() {
  			static const char* sl[] = { "s" }; return sl; }
  
  	protected:
  		bool			_gateDisabled;		// flag indicating disabled by ACh
  		Number			_disabledValue;		// Xinf value when disabled
  		Number			_disabledTau;		// tau value when disabled
  	};
  
  	// Abstract Na channel ------------------------------------------
  
  	class Abstract_Na_channel : public M3HSIonChannel {
  
  	public:
  
  		// Constructor and destructor
  		Abstract_Na_channel() { _sGate=NULL; }
  		virtual ~Abstract_Na_channel() {}
  
  		// Control current s gate status
  		virtual bool	sGateDisabled()					{ return _sGate->gateDisabled(); }
  		virtual void	sGateDisabled(bool status)		{ _sGate->gateDisabled(status); }
  
  		virtual Number	sGateDisabledValue()			{ return _sGate->disabledValue(); }
  		virtual void	sGateDisabledValue(Number x)	{ _sGate->disabledValue(x); }
  
  	protected:
  		Abstract_Na_s_gate*		_sGate;			// subclass must initialize
  	};
  
  	// ================================================================
  	// Na channel class definitions
  	// ================================================================
  
  	// Proximal Na channel -------------------------------------------
  
  	class Proximal_Na_m_gate : public EnergyBarrierTabGate {
  
  	public:
  		// Constructors and destructor
  		Proximal_Na_m_gate() {}
  		virtual ~Proximal_Na_m_gate() {}
  
  		// Estimated temperature sensitivity
  		virtual Number	ratedTempC()	{return  22; }
  		virtual Number	Q10()			{return	 4; }
  
  		// Order 3 gate for Vhalf=-12.0mV, k=8.1mV (Gasparinit & Magee)
  		virtual Number	Vhalf()			{return -25.5*UOM::mV; }
  		virtual Number	slope()			{return  10.0*UOM::mV; }
  
  		// Time constants similar to those in Costa
  		virtual Number	tauMax()		{return 0.2*UOM::msec; }
  		virtual Number	tauMin()		{return 0.05*UOM::msec; }
  		virtual Number	gamma()			{return 0.5f; }
  
  		// State vector label functions
  		virtual const char*	componentName() {return "Na"; }
  		virtual const char** stateLabels() {
  			static const char* sl[] = { "m" }; return sl; }
  
  	protected:
  		virtual AlphaBetaEntry** pAlphaBetaTable() { return &_abTable; }
  
  	private:
  		static AlphaBetaEntry*		_abTable;
  	};
  
  	class Proximal_Na_s_gate : public Abstract_Na_s_gate {
  
  	public:
  		// Constructors and destructor
  		Proximal_Na_s_gate(
  			bool isDisabled=false,	// set gateDisabled on or off
  			Number dval=0.5f)		// set default disabled value
  			: Abstract_Na_s_gate(isDisabled,dval) {}
  
  		virtual ~Proximal_Na_s_gate() {}
  
  		// Steady state inactivation from Gasparini & Magee.
  		virtual Number	Vhalf()			{return -66.8*UOM::mV; }
  		virtual Number	slope()			{return -6.8*UOM::mV; }
  
  		// Time constant. Entry into slow inactivation is reduced
  		// for somatic (and also proximal) channels but recovery
  		// times are the same as for dendrites. This is modeled
  		// by making the time constant less depedent on voltage.
  		virtual Number	tauMax()		{return  1300*UOM::msec; }
  		virtual Number	tauMin()		{return  800*UOM::msec; }
  
  	protected:
  		virtual AlphaBetaEntry** pAlphaBetaTable() { return &_abTable; }
  
  	private:
  		static  AlphaBetaEntry*		_abTable;
  	};
  
  	class Proximal_Na_channel : public Abstract_Na_channel {
  	
  	public:
  		// Constructors and destructor
  		Proximal_Na_channel(
  			Number		gSpVal=0,					// specific conductance value
  			bool		sGateDisabled=false,		// s-gate disabled or not
  			Number		sGateValue=0.5);			// fixed s-gate value if disabled
  		virtual ~Proximal_Na_channel() {}
  
  		// Reversal potential for Na+
  		virtual Number Vrev() { return _Vrev; }
  
  	protected:
  		static const Number		_Vrev;
  	};
  
  	// Distal Na channel -------------------------------------------
  
  	class Distal_Na_m_gate : public EnergyBarrierTabGate {
  
  	public:
  
  		// Constructors and destructor
  		Distal_Na_m_gate() {}
  		virtual ~Distal_Na_m_gate() {}
  
  		// Estimated temperature sensitivity
  		virtual Number	ratedTempC()	{return  22; }
  		virtual Number	Q10()			{return	 4; }
  
  		// Order 3 gate for Vhalf=-20.4mV, k=8.2mV (Gasparinit & Magee)
  		virtual Number	Vhalf()			{return -34.1*UOM::mV; }
  		virtual Number	slope()			{return  10.1*UOM::mV; }
  
  		// Time constants similar to those in Costa
  		virtual Number	tauMax()		{return 0.2*UOM::msec; }
  		virtual Number	tauMin()		{return 0.05*UOM::msec; }
  		virtual Number	gamma()			{return 0.5f; }
  
  		// State vector label functions
  		virtual const char*	componentName() {return "Na"; }
  		virtual const char** stateLabels() { 
  			static const char* sl[] = { "m" }; return sl; }
  
  	protected:
  		virtual AlphaBetaEntry** pAlphaBetaTable() { return &_abTable; }
  
  	private:
  		static AlphaBetaEntry*		_abTable;
  	};
  
  	class Distal_Na_s_gate : public Abstract_Na_s_gate {
  
  	public:
  		// Constructors and destructor
  		Distal_Na_s_gate(
  			bool isDisabled=false,	// set gateDisabled on or off
  			Number dval=0.5f)		// set default disabled value
  			: Abstract_Na_s_gate(isDisabled,dval) {}
  
  		virtual ~Distal_Na_s_gate() {}
  
  		// Steady state inactivation from Gasparini & Magee.
  		virtual Number	Vhalf()			{return -63.6*UOM::mV; }
  		virtual Number	slope()			{return -6.3*UOM::mV; }
  
  		// Time constants (see Mikus et al. figures 7 & 8).
  		virtual Number	tauMax()		{return 1300*UOM::msec; }
  		virtual Number	tauMin()		{return 390*UOM::msec; }
  
  		// For these gates, ignore the disable request
  		// since they are not affected by ACh (Tsubokawa et al)
  		inline  bool	gateDisabled()	{return _gateDisabled; }
  		virtual void	gateDisabled(bool flag) {}
  
  	protected:
  		virtual AlphaBetaEntry** pAlphaBetaTable() { return &_abTable; }
  
  	private:
  		static  AlphaBetaEntry*		_abTable;
  	};
  
  	class Distal_Na_channel : public Abstract_Na_channel {
  	
  	public:
  
  		// Constructors and destructor
  		Distal_Na_channel(
  			Number		gSpVal=0,					// specific conductance value
  			bool		sGateDisabled=false,		// s-gate disabled or not
  			Number		sGateValue=0.5);			// fixed s-gate value if disabled
  		virtual ~Distal_Na_channel() {}
  
  		// Reversal potential for Na+
  		virtual Number Vrev() { return _Vrev; }
  
  	protected:
  		static const Number		_Vrev;
  	};
  
  	// Blended Proximal-Distal Na Channel  ----------------------------
  
  	class Blended_Na_m_gate : public BlendedIonGate {
  	
  	public:
  		// Constructors and destructor
  		Blended_Na_m_gate(Number bratio=0.5) : BlendedIonGate(
  			new Proximal_Na_m_gate,
  			new Distal_Na_m_gate,
  			bratio) {}
  		virtual ~Blended_Na_m_gate() {}
  
  		// State vector label functions
  		virtual const char*	componentName() {return "Na"; }
  		virtual const char**	stateLabels() {
  			static const char* sl[] = { "m" }; return sl; }
  	};
  
  	// Blended_Na_s_gate. One problem here is that this inherits from a
  	// a different hierarchy. Logic for disabling the s-gate is replicated
  	// here and in the blended Na channel.
  
  	class Blended_Na_s_gate : public BlendedIonGate {
  	
  	public:
  		// Constructors and destructor
  		Blended_Na_s_gate(Number bratio=0.5,	// blend ratio
  			bool isDisabled=false,				// set gateDisabled on or off
  			Number dval=0.5f);					// set default disabled value
  		virtual ~Blended_Na_s_gate();
  
  		// Access a switch that turns gate on or off. This is a
  		// pass-thru to the underlying gates
  		inline  bool	gateDisabled()	{return sgate1()->gateDisabled(); }
  		virtual void	gateDisabled(bool flag);
  
  		// Access the static value used when the gate is off.
  		// This is a pass-thru to the underlying gates
  		inline	Number	disabledValue() {return sgate1()->disabledValue(); }
  		virtual void	disabledValue(Number s);
  
  		// State vector label functions
  		virtual const char*	componentName() {return "Na"; }
  		virtual const char**	stateLabels() {
  			static const char* sl[] = { "s" }; return sl; }
  
  	protected:
  		bool			_gateDisabled;
  		Number			_disabledValue;
  
  		// Do casts to get appropriate gate types - ugly but necessary
  		inline  Abstract_Na_s_gate* sgate1() { return (Abstract_Na_s_gate*) gate1(); }
  		inline  Abstract_Na_s_gate* sgate2() { return (Abstract_Na_s_gate*) gate2(); }
  	};
  
  	class Blended_Na_channel : public Abstract_Na_channel {
  	
  	public:
  		// Constructors and destructor
  		Blended_Na_channel(
  			Number		gSpVal=0,					// specific conductance value
  			Number		blendRatio=0.5,				// prox-distal blend ratio
  			bool		sGateDisabled=false,		// s-gate disabled or not
  			Number		sGateValue=0.5);			// fixed s-gate value if disabled
  		virtual ~Blended_Na_channel() {}
  
  		// Control current s gate status
  		virtual bool	sGateDisabled()				{ return _blendedSGate->gateDisabled(); }
  		virtual void	sGateDisabled(bool status)	{ _blendedSGate->gateDisabled(status); }
  
  		virtual Number	sGateDisabledValue()		{ return _blendedSGate->disabledValue(); }
  		virtual void	sGateDisabledValue(Number x) { _blendedSGate->disabledValue(x); }
  
  	protected:
  		Blended_Na_s_gate*		_blendedSGate;
  
  		// Reversal potential for Na+
  		virtual Number Vrev() { return _Vrev; }
  
  	protected:
  		static const Number		_Vrev;
  	};
  
  	// Soma Na channel ------------------------------------------------
  
  	class Soma_Na_m_gate : public EnergyBarrierTabGate {
  
  	public:
  		// Constructors and destructor
  		Soma_Na_m_gate() {}
  		virtual ~Soma_Na_m_gate() {}
  
  		// Estimated temperature sensitivity
  		virtual Number	ratedTempC()	{return  22; }
  		virtual Number	Q10()			{return	 4; }
  
  		// Order 3 gate for vhalf=-30mV,k=6.9mV (Colbert & Pan)
  		// This is very close to values from Magee & Johnston.
  		virtual Number	Vhalf()			{return -42.9*UOM::mV; }
  		virtual Number	slope()			{return  8.4*UOM::mV; }
  
  		// Time constants (see Costa)
  		virtual Number	tauMax()		{return 0.2*UOM::msec; }
  		virtual Number	tauMin()		{return 0.05*UOM::msec; }
  		virtual Number	gamma()			{return 0.5f; }
  
  		// State vector label functions
  		virtual const char*	componentName() {return "Na"; }
  		virtual const char**	stateLabels() {
  			static const char* sl[] = { "m" }; return sl; }
  
  	protected:
  		virtual AlphaBetaEntry** pAlphaBetaTable() { return &_abTable; }
  
  	private:
  		static AlphaBetaEntry*		_abTable;
  	};
  
  	class Soma_Na_s_gate : public Abstract_Na_s_gate {
  
  	public:
  		// Constructors and destructor
  		Soma_Na_s_gate(
  			bool isDisabled=false,	// set gateDisabled on or off
  			Number dval=0.5f)		// set default disabled value
  			: Abstract_Na_s_gate(isDisabled,dval) {}
  
  		virtual ~Soma_Na_s_gate() {}
  
  		// Voltage sensitivity from Colbert & Pan
  		virtual Number	Vhalf()			{return -66*UOM::mV; }
  		virtual Number	slope()			{return -5.3*UOM::mV; }
  
  		// Time constant. Entry into slow inactivation is reduced
  		// for somatic (and also proximal) channels but recovery
  		// times are the same as for dendrites. This is modeled
  		// by making the time constant less depedent on voltage.
  		virtual Number	tauMax()		{return  1300*UOM::msec; }
  		virtual Number	tauMin()		{return  800*UOM::msec; }
  
  	protected:
  		virtual AlphaBetaEntry** pAlphaBetaTable() { return &_abTable; }
  
  	private:
  		static  AlphaBetaEntry*		_abTable;
  	};
  
  	class Soma_Na_channel : public Abstract_Na_channel {
  	
  	public:
  		// Constructors and destructor
  		Soma_Na_channel(
  			Number		gSpVal=0,					// specific conductance value
  			bool		sGateDisabled=false,		// s-gate disabled or not
  			Number		sGateValue=0.5);			// fixed s-gate value if disabled
  		virtual ~Soma_Na_channel() {}
  
  		// Reversal potential for Na+
  		virtual Number Vrev() { return _Vrev; }
  
  	protected:
  		static const Number		_Vrev;
  	};
  
  	// Axon Na channel ------------------------------------------------
  
  	class Axon_Na_m_gate : public EnergyBarrierTabGate {
  
  	public:
  
  		// Constructors and destructor
  		Axon_Na_m_gate() {}
  		virtual ~Axon_Na_m_gate() {}
  
  		// Estimated temperature sensitivity
  		virtual Number	ratedTempC()	{return  22; }
  		virtual Number	Q10()			{return	 4; }
  
  		// Order 3 gate for Vhalf=-38.4mV, k=6.0mV (Colbert & Pan)
  		virtual Number	Vhalf()			{return -48.4*UOM::mV; }
  		virtual Number	slope()			{return  7.3*UOM::mV; }
  
  		// Time constants typical of HH axon measurements and models.
  		// See fit by Colbert & Pan to HH formalism.
  		virtual Number	tauMax()		{return 0.5*UOM::msec; }
  		virtual Number	tauMin()		{return 0.05*UOM::msec; }
  		virtual Number	gamma()			{return 0.5f; }
  
  		// State vector label functions
  		virtual const char*	componentName() {return "Na"; }
  		virtual const char** stateLabels() { 
  			static const char* sl[] = { "m" }; return sl; }
  
  	protected:
  		virtual AlphaBetaEntry** pAlphaBetaTable() { return &_abTable; }
  
  	private:
  		static AlphaBetaEntry*		_abTable;
  	};
  
  	class Axon_Na_h_gate : public EnergyBarrierTabGate {
  
  	public:
  		// Constructors and destructor
  		Axon_Na_h_gate() {}
  		virtual ~Axon_Na_h_gate() {}
  
  		// Values from Colbert & Pan
  		virtual Number	ratedTempC()	{return  22; }
  		virtual Number	Q10()			{return	 2; }
  
  		virtual Number	Vhalf()			{return -69*UOM::mV; }
  		virtual Number	slope()			{return -5.3*UOM::mV; }
  
  		// Time constants similar to Colbert & Pan fit of currents
  		virtual Number	tauMax()		{return 6*UOM::msec; }
  		virtual Number	tauMin()		{return 0.4*UOM::msec; }
  		virtual Number	gamma()			{return 0.5f; }
  
  		// State vector label functions
  		virtual const char*	componentName() {return "Na"; }
  		virtual const char** stateLabels() { 
  			static const char* sl[] = { "h" }; return sl; }
  
  	protected:
  		virtual AlphaBetaEntry** pAlphaBetaTable() { return &_abTable; }
  
  	private:
  		static AlphaBetaEntry*		_abTable;
  	};
  
  	class Axon_Na_channel : public M3HIonChannel {
  	
  	public:
  		// Constructors and destructor
  		Axon_Na_channel(Number gSpVal=0);
  		virtual ~Axon_Na_channel() {}
  
  		// Reversal potential for Na+
  		virtual Number Vrev() { return _Vrev; }
  
  	protected:
  		static const Number		_Vrev;
  	};
  
  
  	// Persistent Na channel ------------------------------------------
  
  	class Persistent_Na_m_gate : public EnergyBarrierTabGate {
  
  	public:
  
  		// Constructors and destructor
  		Persistent_Na_m_gate() {}
  		virtual ~Persistent_Na_m_gate() {}
  
  		virtual Number	ratedTempC()	{return  22; }
  		virtual Number	Q10()			{return	 3; } // assumed Q10
  
  		// Voltage sensitivity (Magistretti & Alonso 1999 in situ)
  		virtual Number	Vhalf()			{return -51.3*UOM::mV; }
  		virtual Number	slope()			{return  4.0*UOM::mV; }
  
  		// Time constant (see Magistretti & Alonso 2002)
  		// These are based on decay and first latency times,
  		// but obviously this model oversimplifies the kinetics.
  		virtual Number	tauMax()		{return  18*UOM::msec; }
  		virtual Number	tauMin()		{return  0.3*UOM::msec; }
  
  		// State vector label functions
  		virtual const char*	componentName() {return "NaP"; }
  		virtual const char** stateLabels() { 
  			static const char* sl[] = { "m" }; return sl; }
  
  	protected:
  		virtual AlphaBetaEntry**	pAlphaBetaTable() { return &_abTable; }
  
  	private:
  		static AlphaBetaEntry*		_abTable;
  	};
  
  	class Persistent_Na_h_gate : public EnergyBarrierTabGate {
  
  	public:
  
  		// Constructors and destructor
  		Persistent_Na_h_gate() {}
  		virtual ~Persistent_Na_h_gate() {}
  
  		virtual Number	ratedTempC()	{return  22; }
  		virtual Number	Q10()			{return	 1; } // unknown Q10
  
  		// Voltage sensitivity (see Magistretti & Alonso 1999)
  		virtual Number	Vhalf()			{return -48.4*UOM::mV; }
  		virtual Number	slope()			{return -10.0*UOM::mV; }
  
  		// Time constant (see Magistretti & Alonso 1999)
  		virtual Number	tauMax()		{return  6.0*UOM::sec; }
  		virtual Number	tauMin()		{return  2.0*UOM::sec; }
  		virtual Number	gamma()			{return  0.2f; }
  
  		// State vector label functions
  		virtual const char*	componentName() {return "NaP"; }
  		virtual const char**	stateLabels() { 
  			static const char* sl[] = { "h" }; return sl; }
  
  	protected:
  		virtual AlphaBetaEntry**	pAlphaBetaTable() { return &_abTable; }
  
  	private:
  		static AlphaBetaEntry*		_abTable;
  	};
  
  	class Persistent_Na_channel : public M1HIonChannel {
  
  	public:
  
  		// Constructors and destructor
  		Persistent_Na_channel(Number gSpVal);
  		virtual ~Persistent_Na_channel() {}
  
  		// Reversal potential for Na+
  		virtual Number Vrev() { return _Vrev; }
  
  	protected:
  		static const Number			_Vrev;
  	};
  
  };
  
  #endif // #ifndef __IONCHAN_NA_BAKER_2003_H_
  