glif_psc_double_alpha#
- class brainpy.state.glif_psc_double_alpha(in_size, g=Quantity(9.43, 'nS'), E_L=Quantity(-78.85, 'mV'), V_th=Quantity(-51.68, 'mV'), C_m=Quantity(58.72, 'pF'), t_ref=Quantity(3.75, 'ms'), V_reset=Quantity(-78.85, 'mV'), th_spike_add=0.37, th_spike_decay=0.009, voltage_reset_fraction=0.2, voltage_reset_add=18.51, th_voltage_index=0.005, th_voltage_decay=0.09, asc_init=(0.0, 0.0), asc_decay=(0.003, 0.1), asc_amps=(-9.18, -198.94), asc_r=(1.0, 1.0), tau_syn_fast=(2.0,), tau_syn_slow=(6.0,), amp_slow=(0.3,), spike_dependent_threshold=False, after_spike_currents=False, adapting_threshold=False, I_e=Quantity(0., 'pA'), gsl_error_tol=1e-06, V_initializer=None, spk_fun=ReluGrad(alpha=0.3, width=1.0), spk_reset='hard', name=None)#
Current-based generalized leaky integrate-and-fire (GLIF) neuron model with double alpha-function shaped synaptic currents.
Implements the NEST
glif_psc_double_alphamodel, which extends the basic GLIF framework [1] with dual-component (fast + slow) alpha-function shaped postsynaptic currents [2]. This allows flexible control over synaptic waveform shape, including realistic biphasic or long-tailed currents observed experimentally. The model provides five GLIF variants (Models 1-5) selectable via boolean flags, ranging from simple LIF to adaptive threshold models with after-spike currents.Model Family Overview
The five GLIF models are hierarchical, each adding biological mechanisms:
GLIF Model 1 (LIF) — Traditional leaky integrate-and-fire
GLIF Model 2 (LIF_R) — LIF with biologically defined reset rules
GLIF Model 3 (LIF_ASC) — LIF with after-spike currents
GLIF Model 4 (LIF_R_ASC) — LIF with reset rules and after-spike currents
GLIF Model 5 (LIF_R_ASC_A) — LIF with reset rules, after-spike currents, and a voltage-dependent threshold
Model selection is determined by three boolean parameters:
Model
spike_dependent_threshold
after_spike_currents
adapting_threshold
GLIF1
False
False
False
GLIF2
True
False
False
GLIF3
False
True
False
GLIF4
True
True
False
GLIF5
True
True
True
Double Alpha-Function Synaptic Currents
Each synaptic receptor port receives inputs shaped by a sum of two alpha functions (fast and slow components) [2]:
\[I_\mathrm{syn,k}(t) = \alpha_\mathrm{fast}(t; \tau_{\mathrm{syn,fast},k}) + \mathrm{amp\_slow}_k \cdot \alpha_\mathrm{slow}(t; \tau_{\mathrm{syn,slow},k})\]Normalization: A spike of weight 1.0 produces a peak current of 1 pA for the fast component at \(t = \tau_\mathrm{syn,fast}\). The slow component peaks at \(\mathrm{amp\_slow}_k\) pA at \(t = \tau_\mathrm{syn,slow}\).
Multiple receptor ports are supported by passing arrays to
tau_syn_fast,tau_syn_slow, andamp_slow. By default, one receptor port is created. Projections specify receptor ports viareceptor_<k>labels (0-based indexing).Detailed Mathematical Description
1. Membrane Dynamics
The membrane potential \(U\) (tracked relative to \(E_L\)) evolves via exact integration using propagator matrices:
\[U(t+dt) = U(t) \cdot P_{33} + (I_e + I_\mathrm{stim} + I_\mathrm{ASC,sum}) \cdot P_{30} + \sum_k \left( P_{31,k}^\mathrm{fast} \cdot y_{1,k}^\mathrm{fast} + P_{32,k}^\mathrm{fast} \cdot y_{2,k}^\mathrm{fast} \right) + \sum_k \left( P_{31,k}^\mathrm{slow} \cdot y_{1,k}^\mathrm{slow} + P_{32,k}^\mathrm{slow} \cdot y_{2,k}^\mathrm{slow} \right)\]where:
\[P_{33} = \exp\left(-\frac{dt}{\tau_m}\right), \quad P_{30} = \frac{\tau_m}{C_m} \left(1 - P_{33}\right), \quad \tau_m = \frac{C_m}{g}\]The propagators \(P_{31,k}\), \(P_{32,k}\) for each receptor and component (fast/slow) are computed using the
IAFPropagatorAlphaalgorithm, which handles the singularity when \(\tau_m \approx \tau_{\mathrm{syn},k}\).2. Synaptic Current Dynamics (Double Alpha Function)
Each receptor port \(k\) maintains four state variables: two for the fast component and two for the slow component. Each pair \((y_1, y_2)\) represents an alpha function.
Fast component:
\[y_{2,k}^\mathrm{fast}(t+dt) = P_{21,k}^\mathrm{fast} \cdot y_{1,k}^\mathrm{fast}(t) + P_{22,k}^\mathrm{fast} \cdot y_{2,k}^\mathrm{fast}(t)\]\[y_{1,k}^\mathrm{fast}(t+dt) = P_{11,k}^\mathrm{fast} \cdot y_{1,k}^\mathrm{fast}(t)\]Slow component:
\[y_{2,k}^\mathrm{slow}(t+dt) = P_{21,k}^\mathrm{slow} \cdot y_{1,k}^\mathrm{slow}(t) + P_{22,k}^\mathrm{slow} \cdot y_{2,k}^\mathrm{slow}(t)\]\[y_{1,k}^\mathrm{slow}(t+dt) = P_{11,k}^\mathrm{slow} \cdot y_{1,k}^\mathrm{slow}(t)\]where:
\[ \begin{align}\begin{aligned}P_{11,k}^\mathrm{fast} = P_{22,k}^\mathrm{fast} = \exp\left(-\frac{dt}{\tau_{\mathrm{syn,fast},k}}\right)\\P_{21,k}^\mathrm{fast} = dt \cdot P_{11,k}^\mathrm{fast}\\P_{11,k}^\mathrm{slow} = P_{22,k}^\mathrm{slow} = \exp\left(-\frac{dt}{\tau_{\mathrm{syn,slow},k}}\right)\\P_{21,k}^\mathrm{slow} = dt \cdot P_{11,k}^\mathrm{slow}\end{aligned}\end{align} \]On a presynaptic spike of weight \(w\) to receptor port \(k\):
\[ \begin{align}\begin{aligned}y_{1,k}^\mathrm{fast} \leftarrow y_{1,k}^\mathrm{fast} + w \cdot \frac{e}{\tau_{\mathrm{syn,fast},k}}\\y_{1,k}^\mathrm{slow} \leftarrow y_{1,k}^\mathrm{slow} + w \cdot \frac{e}{\tau_{\mathrm{syn,slow},k}} \cdot \mathrm{amp\_slow}_k\end{aligned}\end{align} \]The total synaptic current is:
\[I_\mathrm{syn,total} = \sum_k \left( y_{2,k}^\mathrm{fast} + y_{2,k}^\mathrm{slow} \right)\]3. After-Spike Currents (GLIF3/4/5)
After-spike currents (ASC) model slow adaptation via exponentially decaying currents triggered by spikes. Each ASC component \(I_j\) decays with rate \(k_j\):
\[I_j(t+dt) = I_j(t) \cdot \exp(-k_j \cdot dt)\]The time-averaged ASC over a step (used for stable integration) is:
\[\bar{I}_j = \frac{1 - \exp(-k_j \cdot dt)}{k_j \cdot dt} \cdot I_j(t)\]On spike, ASC values are reset:
\[I_j \leftarrow \Delta I_j + I_j \cdot r_j \cdot \exp(-k_j \cdot t_\mathrm{ref})\]where \(\Delta I_j\) is the jump amplitude and \(r_j\) is the fraction coefficient.
4. Spike-Dependent Threshold (GLIF2/4/5)
The spike component of the threshold \(\theta_s\) decays exponentially:
\[\theta_s(t+dt) = \theta_s(t) \cdot \exp(-b_s \cdot dt)\]On spike, after refractory decay:
\[\theta_s \leftarrow \theta_s \cdot \exp(-b_s \cdot t_\mathrm{ref}) + \Delta\theta_s\]Voltage reset uses a biologically defined rule:
\[U \leftarrow f_v \cdot U_\mathrm{old} + V_\mathrm{add}\]where \(f_v\) is the voltage fraction coefficient and \(V_\mathrm{add}\) is the additive constant.
5. Voltage-Dependent Threshold (GLIF5)
The voltage component of the threshold \(\theta_v\) evolves according to:
\[\theta_v(t+dt) = \phi \cdot (U_\mathrm{old} - \beta) \cdot P_\mathrm{decay} + \frac{1}{P_{\theta,v}} \cdot \left(\theta_v(t) - \phi \cdot (U_\mathrm{old} - \beta) - \frac{a_v}{b_v} \cdot \beta \right) + \frac{a_v}{b_v} \cdot \beta\]where:
\[\phi = \frac{a_v}{b_v - g/C_m}, \quad P_\mathrm{decay} = \exp\left(-\frac{g \cdot dt}{C_m}\right), \quad P_{\theta,v} = \exp(b_v \cdot dt), \quad \beta = \frac{I_e + I_\mathrm{stim} + I_\mathrm{ASC,sum}}{g}\]6. Overall Threshold and Spike Condition
\[\theta_\mathrm{total} = \theta_\infty + \theta_s + \theta_v\]Spike condition (checked after voltage update):
\[\begin{split}\text{spike} = \begin{cases} \text{True} & \text{if } U > \theta_\mathrm{total} \\ \text{False} & \text{otherwise} \end{cases}\end{split}\]7. Numerical Integration and Update Order
The discrete-time update sequence per simulation step is:
Record \(U_\mathrm{old}\) (relative to \(E_L\)).
If not refractory:
Decay spike threshold component \(\theta_s\).
Compute time-averaged ASC \(\bar{I}_j\) and decay ASC values.
Update membrane potential \(U\) (include fast/slow synaptic contributions).
Compute voltage-dependent threshold component \(\theta_v\) (using \(U_\mathrm{old}\)).
Update total threshold \(\theta_\mathrm{total}\).
If \(U > \theta_\mathrm{total}\): emit spike, apply reset rules.
If refractory: decrement refractory counter, hold \(U\) at \(U_\mathrm{old}\).
Update synaptic current state variables for both fast and slow components.
Add incoming spike current jumps (scaled for fast/slow).
Buffer external current input for next step.
Save \(U_\mathrm{old}\) for next step.
- Parameters:
in_size (
int,tupleofint) – Population shape (number of neurons). Scalars are interpreted as (n,).g (
ArrayLike, optional) – Membrane (leak) conductance. Default: 9.43 nS. Must be strictly positive. Shape: scalar or broadcastable toin_size.E_L (
ArrayLike, optional) – Resting (leak) membrane potential (absolute). Default: -78.85 mV. Shape: scalar or broadcastable toin_size.V_th (
ArrayLike, optional) – Instantaneous spike threshold (absolute). Default: -51.68 mV. Must be greater thanV_reset. Shape: scalar or broadcastable toin_size.C_m (
ArrayLike, optional) – Membrane capacitance. Default: 58.72 pF. Must be strictly positive. Shape: scalar or broadcastable toin_size.t_ref (
ArrayLike, optional) – Absolute refractory period. Default: 3.75 ms. Must be strictly positive. Shape: scalar or broadcastable toin_size.V_reset (
ArrayLike, optional) – Reset potential (absolute; used in GLIF1/3). Default: -78.85 mV. Must be less thanV_th. Shape: scalar or broadcastable toin_size.th_spike_add (
float, optional) – Threshold additive constant after spike (\(\Delta\theta_s\)). Default: 0.37 mV. Used in GLIF2/4/5.th_spike_decay (
float, optional) – Spike threshold decay rate (\(b_s\)). Default: 0.009 /ms. Must be strictly positive. Used in GLIF2/4/5.voltage_reset_fraction (
float, optional) – Voltage fraction coefficient after spike (\(f_v\)). Default: 0.20. Must be in [0.0, 1.0]. Used in GLIF2/4/5.voltage_reset_add (
float, optional) – Voltage additive constant after spike (\(V_\mathrm{add}\)). Default: 18.51 mV. Used in GLIF2/4/5.th_voltage_index (
float, optional) – Voltage-dependent threshold leak rate (\(a_v\)). Default: 0.005 /ms. Used in GLIF5.th_voltage_decay (
float, optional) – Voltage-dependent threshold decay rate (\(b_v\)). Default: 0.09 /ms. Must be strictly positive. Used in GLIF5.asc_init (
Sequence[float], optional) – Initial values of after-spike current components (pA). Default: (0.0, 0.0). Length must matchasc_decay,asc_amps,asc_r. Used in GLIF3/4/5.asc_decay (
Sequence[float], optional) – After-spike current decay rates (\(k_j\), /ms). Default: (0.003, 0.1). All values must be strictly positive. Used in GLIF3/4/5.asc_amps (
Sequence[float], optional) – After-spike current jump amplitudes (\(\Delta I_j\), pA). Default: (-9.18, -198.94). Used in GLIF3/4/5.asc_r (
Sequence[float], optional) – After-spike current fraction coefficients (\(r_j\)). Default: (1.0, 1.0). All values must be in [0.0, 1.0]. Used in GLIF3/4/5.tau_syn_fast (
Sequence[float], optional) – Fast synaptic alpha-function time constants (ms). Default: (2.0,). All values must be strictly positive. Length determines number of receptor ports.tau_syn_slow (
Sequence[float], optional) – Slow synaptic alpha-function time constants (ms). Default: (6.0,). All values must be strictly positive. Length must matchtau_syn_fast.amp_slow (
Sequence[float], optional) – Relative amplitude of slow component (unitless). Default: (0.3,). All values must be strictly positive. Length must matchtau_syn_fast.spike_dependent_threshold (
bool, optional) – Enable biologically defined reset rules (GLIF2/4/5). Default: False.after_spike_currents (
bool, optional) – Enable after-spike currents (GLIF3/4/5). Default: False.adapting_threshold (
bool, optional) – Enable voltage-dependent threshold (GLIF5). Default: False.I_e (
ArrayLike, optional) – Constant external current input (pA). Default: 0.0 pA. Shape: scalar or broadcastable toin_size.V_initializer (
Callable, optional) – Membrane potential initializer. Default:Constant(E_L). Should return values in mV when called with shape and batch_size.spk_fun (
Callable, optional) – Surrogate gradient function for differentiable spike generation. Default:ReluGrad(). Must accept scaled voltage and return spike output.spk_reset (
str, optional) – Spike reset mode. Default:'hard'(stop gradient). Alternative:'soft'.name (
str, optional) – Name of this neuron population.
Parameter Mapping
Parameter
Default
Math equivalent
Description
in_size(required)
—
Population shape
g9.43 nS
\(g\)
Membrane (leak) conductance
E_L-78.85 mV
\(E_L\)
Resting membrane potential
V_th-51.68 mV
\(V_\mathrm{th}\)
Instantaneous threshold (absolute)
C_m58.72 pF
\(C_m\)
Membrane capacitance
t_ref3.75 ms
\(t_\mathrm{ref}\)
Absolute refractory period
V_reset-78.85 mV
\(V_\mathrm{reset}\)
Reset potential (absolute; GLIF1/3)
th_spike_add0.37 mV
\(\Delta\theta_s\)
Threshold additive constant after spike
th_spike_decay0.009 /ms
\(b_s\)
Spike threshold decay rate
voltage_reset_fraction0.20
\(f_v\)
Voltage fraction after spike
voltage_reset_add18.51 mV
\(V_\mathrm{add}\)
Voltage additive after spike
th_voltage_index0.005 /ms
\(a_v\)
Voltage-dependent threshold leak
th_voltage_decay0.09 /ms
\(b_v\)
Voltage-dependent threshold decay rate
asc_init(0.0, 0.0) pA
\(I_j(0)\)
Initial values of ASC
asc_decay(0.003, 0.1) /ms
\(k_j\)
ASC decay rates
asc_amps(-9.18, -198.94) pA
\(\Delta I_j\)
ASC amplitudes on spike
asc_r(1.0, 1.0)
\(r_j\)
ASC fraction coefficient
tau_syn_fast(2.0,) ms
\(\tau_{\mathrm{syn,fast},k}\)
Fast synaptic alpha-function time constants
tau_syn_slow(6.0,) ms
\(\tau_{\mathrm{syn,slow},k}\)
Slow synaptic alpha-function time constants
amp_slow(0.3,)
\(\mathrm{amp\_slow}_k\)
Relative amplitude of slow component
spike_dependent_thresholdFalse
—
Enable biologically defined reset (GLIF2/4/5)
after_spike_currentsFalse
—
Enable after-spike currents (GLIF3/4/5)
adapting_thresholdFalse
—
Enable voltage-dependent threshold (GLIF5)
I_e0.0 pA
\(I_e\)
Constant external current
V_initializerConstant(E_L)
—
Membrane potential initializer
spk_funReluGrad()
—
Surrogate spike function
spk_reset'hard'—
Reset mode (
'hard'or'soft')Notes
Default parameters are from GLIF Model 5 of Cell 490626718 in the Allen Cell Type Database (https://celltypes.brain-map.org).
Voltage tracking:
V_thandV_resetare specified in absolute mV. Internally, membrane potential is stored relative toE_L(matching NEST).Stability constraint for GLIF2/4/5: The reset condition should satisfy:
\[E_L + f_v \cdot (V_\mathrm{th} - E_L) + V_\mathrm{add} < V_\mathrm{th} + \Delta\theta_s\]Otherwise, the neuron may spike continuously.
Numerical integration: Uses exact integration via propagator matrices (matching NEST), unlike
glif_condwhich uses RKF45 ODE integration.Singularity handling: If \(\tau_m \approx \tau_{\mathrm{syn,fast}}\) or \(\tau_m \approx \tau_{\mathrm{syn,slow}}\), the model automatically applies singularity-safe formulas (see NEST IAF_Integration_Singularity notebook).
Synaptic waveform control: The double alpha function provides more flexible control over synaptic current shape compared to single alpha (
glif_psc). By tuningtau_syn_fast,tau_syn_slow, andamp_slow, experimentally observed waveforms can be matched.Receptor port indexing: Synaptic inputs are registered via
add_delta_input()with labels like'receptor_0','receptor_1', etc. Inputs without explicit receptor labels default to receptor 0.State persistence: After-spike current values (
_ASCurrents), threshold components (_threshold_spike,_threshold_voltage), and total threshold (_threshold) are stored as NumPy arrays (not JAX arrays) to match NEST’s state handling and allow in-place updates during the per-neuron loop.
Examples
1. GLIF Model 1 (basic LIF) with single receptor:
>>> import brainpy.state as st >>> import brainstate as bst >>> import saiunit as u >>> bst.environ.set(dt=0.1 * u.ms) >>> neurons = st.glif_psc_double_alpha( ... in_size=100, ... g=10.0 * u.nS, ... E_L=-70.0 * u.mV, ... V_th=-55.0 * u.mV, ... C_m=250.0 * u.pF, ... t_ref=2.0 * u.ms, ... V_reset=-70.0 * u.mV, ... tau_syn_fast=(2.0,) * u.ms, ... tau_syn_slow=(6.0,) * u.ms, ... amp_slow=(0.5,), ... ) >>> neurons.init_all_states() >>> spikes = neurons.update(10.0 * u.pA)
2. GLIF Model 5 (full model) with multiple receptors:
>>> neurons = st.glif_psc_double_alpha( ... in_size=50, ... spike_dependent_threshold=True, ... after_spike_currents=True, ... adapting_threshold=True, ... tau_syn_fast=(1.0, 3.0) * u.ms, # Two receptor ports ... tau_syn_slow=(5.0, 10.0) * u.ms, ... amp_slow=(0.3, 0.4), ... asc_decay=(0.01, 0.05) / u.ms, ... asc_amps=(-10.0, -100.0) * u.pA, ... ) >>> neurons.init_all_states() >>> # Synaptic inputs can target different receptors >>> neurons.add_delta_input('excitatory_receptor_0') >>> neurons.add_delta_input('inhibitory_receptor_1')
3. Accessing synaptic current components:
>>> I_syn_total = neurons.get_I_syn() >>> I_syn_fast = neurons.get_I_syn_fast() >>> I_syn_slow = neurons.get_I_syn_slow()
References
See also
glif_pscSingle alpha-function variant.
glif_condConductance-based GLIF using ODE integration.
gif_psc_exp_multisynapseGeneralized IF with exponential PSCs and multisynapse support.
aeif_psc_alphaAdaptive exponential IF with alpha PSCs.
- get_I_syn()[source]#
Get the total synaptic current summed across all receptor ports and components.
Computes the instantaneous total synaptic current by summing the fast and slow alpha-function current components (
y2_fastandy2_slow) across all receptor ports. This represents the total postsynaptic current \(I_\mathrm{syn}\) flowing into the membrane at the current time step.- Returns:
I_syn – Total synaptic current across all receptors (fast + slow). Shape: same as
self.V.value.shape(including batch dimension if present). Unit:saiunit.pA(picoamperes).- Return type:
jax.Array
Notes
This method reads the current state of
y2_fast[k]andy2_slow[k]for all receptor portsk, without modifying state.For a population with \(N\) receptor ports, the total current is:
\[I_\mathrm{syn,total} = \sum_{k=0}^{N-1} \left( y_{2,k}^\mathrm{fast} + y_{2,k}^\mathrm{slow} \right)\]
See also
get_I_syn_fastGet only the fast component.
get_I_syn_slowGet only the slow component.
- get_I_syn_fast()[source]#
Get the fast component of synaptic current summed across all receptor ports.
Computes the instantaneous fast synaptic current by summing the fast alpha-function current components (
y2_fast) across all receptor ports. The fast component corresponds to synaptic currents with time constanttau_syn_fast.- Returns:
I_syn_fast – Fast synaptic current across all receptors. Shape: same as
self.V.value.shape(including batch dimension if present). Unit:saiunit.pA(picoamperes).- Return type:
jax.Array
Notes
For a population with \(N\) receptor ports, the fast current is:
\[I_\mathrm{syn,fast} = \sum_{k=0}^{N-1} y_{2,k}^\mathrm{fast}\]
See also
get_I_synGet total synaptic current (fast + slow).
get_I_syn_slowGet only the slow component.
- get_I_syn_slow()[source]#
Get the slow component of synaptic current summed across all receptor ports.
Computes the instantaneous slow synaptic current by summing the slow alpha-function current components (
y2_slow) across all receptor ports. The slow component corresponds to synaptic currents with time constanttau_syn_slow, scaled by amplitude factoramp_slow.- Returns:
I_syn_slow – Slow synaptic current across all receptors. Shape: same as
self.V.value.shape(including batch dimension if present). Unit:saiunit.pA(picoamperes).- Return type:
jax.Array
Notes
For a population with \(N\) receptor ports, the slow current is:
\[I_\mathrm{syn,slow} = \sum_{k=0}^{N-1} y_{2,k}^\mathrm{slow}\]The slow component typically models NMDA-like or other slow synaptic processes.
See also
get_I_synGet total synaptic current (fast + slow).
get_I_syn_fastGet only the fast component.
- get_spike(V=None)[source]#
Compute spike output from membrane potential using surrogate gradient function.
Applies the surrogate gradient function (
self.spk_fun) to a scaled version of the membrane potential to produce a differentiable spike signal. This method computes the spike output without updating state, making it useful for inspection or custom integration schemes.Scaling
The membrane potential is scaled to the range where the surrogate function is most sensitive:
\[v_\mathrm{scaled} = \frac{V - V_\mathrm{th}}{V_\mathrm{th} - V_\mathrm{reset}}\]This normalization ensures that:
When \(V = V_\mathrm{th}\), \(v_\mathrm{scaled} = 0\)
When \(V = V_\mathrm{reset}\), \(v_\mathrm{scaled} = -1\)
- Parameters:
V (
ArrayLike, optional) – Membrane potential (absolute, in mV). IfNone(default), uses the current stateself.V.value. If provided, should have shape compatible withself.varshape(or(batch_size, *self.varshape)). Unit:saiunit.mVor dimensionless (interpreted as mV).- Returns:
spike – Spike output computed via surrogate gradient function. Shape: same as input
V. Dtype: same as inputV(typicallyjnp.float32). Values: Continuous in [0, 1] for most surrogate functions (e.g.,ReluGrad,SigmoidGrad), though exact range depends onself.spk_fun.- Return type:
jax.Array
Notes
This method is used internally by
update()to compute spike output after the membrane potential update.The surrogate gradient function ensures gradients can flow through spike events during backpropagation, enabling gradient-based training of spiking neural networks.
The scaling factor \((V_\mathrm{th} - V_\mathrm{reset})\) normalizes the input to the surrogate function, improving numerical stability and gradient flow.
See also
updateMain simulation step, which calls this method internally.
braintools.surrogate.ReluGradDefault surrogate gradient function.
- init_state(**kwargs)[source]#
Initialize all state variables for the neuron population.
Creates and initializes all state variables required for GLIF dynamics, including membrane potential, synaptic current states (fast and slow components for each receptor port), threshold components, after-spike current values, refractory counters, and buffered input current.
This method is compatible with
brainstate.transform.for_loop: all GLIF-specific state variables are stored as JAXHiddenStatearrays, and pre-computed decay constants are stored as Python floats.- Parameters:
**kwargs – Unused compatibility parameters accepted by the base-state API.
- property n_receptors#
Number of synaptic receptor ports.
Returns the number of distinct receptor ports configured for this neuron population. Each receptor port has independent fast and slow alpha-function current dynamics, allowing modeling of multiple synaptic receptor types (e.g., AMPA, NMDA, GABA_A, GABA_B).
- Returns:
Number of receptor ports, determined by the length of
tau_syn_fast(which must match the lengths oftau_syn_slowandamp_slow).- Return type:
Notes
Receptor ports are indexed from 0 to
n_receptors - 1.Projections target specific receptors via labels like
'receptor_0','receptor_1', etc.By default (single-element arrays for synaptic parameters),
n_receptors == 1.
See also
_collect_receptor_delta_inputsRoutes synaptic inputs to receptor ports.
- update(x=Quantity(0., 'pA'))[source]#
Perform a single simulation step using exact propagator matrices.
Implements the NEST
glif_psc_double_alphaupdate using the exact IAFPropagatorAlpha integration scheme. All GLIF-specific discrete updates (threshold decay, ASC, voltage-dependent threshold) are applied as vectorised JAX operations, making this method compatible withbrainstate.transform.for_loop.- Parameters:
x (
ArrayLike, optional) – External current input (pA), applied with one-step delay. Default: 0.0 pA.- Returns:
spike – Binary spike tensor (float32), shape
(*varshape).- Return type:
jax.Array