gif_psc_exp_multisynapse#

class brainpy.state.gif_psc_exp_multisynapse(in_size, g_L=Quantity(4., "nS"), E_L=Quantity(-70., "mV"), C_m=Quantity(80., "pF"), V_reset=Quantity(-55., "mV"), Delta_V=Quantity(0.5, "mV"), V_T_star=Quantity(-35., "mV"), lambda_0=1.0, t_ref=Quantity(4., "ms"), tau_syn=(2.0, ), I_e=Quantity(0., "pA"), tau_sfa=(), q_sfa=(), tau_stc=(), q_stc=(), rng_key=None, V_initializer=Constant(value=-70. mV), spk_fun=ReluGrad(alpha=0.3, width=1.0), spk_reset='hard', name=None, gsl_error_tol=1e-06)#

Current-based generalized integrate-and-fire neuron (GIF) model with multiple synaptic time constants.

This model implements the multisynapse extension of the generalized integrate-and-fire neuron according to Mensi et al. (2012) [1] and Pozzorini et al. (2015) [2], with exponential postsynaptic currents and an arbitrary number of receptor ports. It is a faithful re-implementation of the NEST simulator’s gif_psc_exp_multisynapse model, preserving exact (analytic) propagator integration, stochastic firing dynamics, update ordering, and all default parameter values.

The model combines four key features:

  1. Multiple receptor ports: Each with independent exponential synaptic time constants (tau_syn parameter)

  2. Spike-triggered currents (STC): Post-spike current injection with multiple time scales (tau_stc, q_stc parameters)

  3. Spike-frequency adaptation (SFA): Dynamic threshold modulation after each spike (tau_sfa, q_sfa parameters)

  4. Stochastic spiking: Exponential escape-rate firing with parameter lambda_0 and threshold noise Delta_V

Mathematical Model

1. Membrane Potential Dynamics

The subthreshold membrane potential \(V(t)\) evolves according to:

\[C_m \frac{dV}{dt} = -g_L (V - E_L) - \sum_j \eta_j(t) + \sum_k I_{\mathrm{syn},k}(t) + I_e + I_{\mathrm{stim}}(t)\]

where:

  • \(g_L (V - E_L)\) is the passive leak current

  • \(\eta_j(t)\) are spike-triggered currents (STCs)

  • \(I_{\mathrm{syn},k}(t)\) are synaptic currents for each receptor port \(k\)

  • \(I_e\) is a constant external bias current

  • \(I_{\mathrm{stim}}(t)\) is time-varying external input

2. Synaptic Currents (Multi-Receptor)

Each receptor port \(k\) has an independent exponential synaptic current:

\[\frac{dI_{\mathrm{syn},k}}{dt} = -\frac{I_{\mathrm{syn},k}}{\tau_{\mathrm{syn},k}}\]

The number of receptor ports is determined by len(tau_syn). When connecting projections, specify receptor_type (1-based indexing, matching NEST convention) to target a specific port. Both excitatory and inhibitory connections can target any receptor port (weights can be positive or negative).

3. Spike-Triggered Currents (STC)

Each STC element \(\eta_j\) evolves as:

\[\tau_{\eta_j} \frac{d\eta_j}{dt} = -\eta_j\]

Upon spike emission at time \(t_{\mathrm{sp}}\):

\[\eta_j(t_{\mathrm{sp}}^+) = \eta_j(t_{\mathrm{sp}}^-) + q_{\eta_j}\]

The total STC contribution is \(\sum_j \eta_j(t)\). STCs can model post-spike currents such as afterhyperpolarization (AHP) or afterdepolarization (ADP) depending on the sign of q_stc.

4. Spike-Frequency Adaptation (SFA)

The firing threshold is dynamic, consisting of a base threshold \(V_{T^*}\) plus adaptive components:

\[V_T(t) = V_{T^*} + \sum_i \gamma_i(t)\]

Each SFA element \(\gamma_i\) evolves as:

\[\tau_{\gamma_i} \frac{d\gamma_i}{dt} = -\gamma_i\]

Upon spike emission:

\[\gamma_i(t_{\mathrm{sp}}^+) = \gamma_i(t_{\mathrm{sp}}^-) + q_{\gamma_i}\]

Positive q_sfa values increase the threshold after each spike, leading to spike-frequency adaptation.

5. Stochastic Spiking Mechanism

The neuron fires stochastically with an exponential escape-rate intensity:

\[\lambda(t) = \lambda_0 \exp\!\left(\frac{V(t) - V_T(t)}{\Delta_V}\right)\]

The probability of firing within a time step \(dt\) is:

\[P_{\mathrm{spike}}(\Delta t) = 1 - \exp(-\lambda(t) \cdot dt)\]

At each non-refractory time step, a uniform random number \(r \in [0, 1)\) is drawn. If \(r < P_{\mathrm{spike}}\), a spike is emitted. The stochasticity level \(\Delta_V\) controls the sharpness of the firing threshold (smaller values → more deterministic).

6. Refractory Period

After a spike, the neuron enters an absolute refractory period of duration \(t_{\mathrm{ref}}\). During this period:

  • The membrane potential is clamped to \(V_{\mathrm{reset}}\)

  • No spike can be emitted (firing intensity check is skipped)

  • Synaptic currents continue to evolve and receive inputs

  • STC and SFA elements continue to decay

Numerical Integration

The model uses exact (analytic) integration for all linear ODEs, matching NEST’s propagator-based integration scheme. For each variable with dynamics \(\tau \frac{dx}{dt} = -x + f(t)\), the update over one time step \(h\) is:

\[x(t + h) = e^{-h/\tau} x(t) + \int_0^h e^{-(h-s)/\tau} f(t+s) \, ds\]

For constant \(f\), this yields exact propagator coefficients. The membrane potential propagator accounts for coupling between \(V\) and synaptic currents with potentially different time constants.

Update Order (Matching NEST)

Each simulation step follows this exact sequence (matching NEST’s gif_psc_exp_multisynapse::update implementation):

Step 1: Adaptation Decay
  • Compute total STC: \(\mathrm{stc\_total} = \sum_j \eta_j(t)\)

  • Compute total threshold: \(V_T(t) = V_{T^*} + \sum_i \gamma_i(t)\)

  • Decay all STC elements: \(\eta_j \leftarrow \eta_j \cdot e^{-dt/\tau_{\eta_j}}\)

  • Decay all SFA elements: \(\gamma_i \leftarrow \gamma_i \cdot e^{-dt/\tau_{\gamma_i}}\)

Step 2: Synaptic Current Processing (per receptor)
For each receptor port \(k\):
  • Compute propagated contribution to \(V\): \(\Delta V_k = P_{21,k} \cdot I_{\mathrm{syn},k}(t)\)

  • Decay synaptic current: \(I_{\mathrm{syn},k} \leftarrow I_{\mathrm{syn},k} \cdot e^{-dt/\tau_{\mathrm{syn},k}}\)

  • Add incoming spike weights: \(I_{\mathrm{syn},k} \leftarrow I_{\mathrm{syn},k} + w_k\)

Step 3: Membrane Update and Spike Check
If not refractory:
  • Update membrane potential using exact propagator:

    \[V(t+dt) = P_{33} V(t) + P_{31} E_L + P_{30}(I_{\mathrm{stim}}(t) + I_e - \mathrm{stc\_total}) + \sum_k \Delta V_k\]
  • Compute firing intensity: \(\lambda = \lambda_0 \exp((V - V_T)/\Delta_V)\)

  • Compute spike probability: \(p = 1 - \exp(-\lambda \cdot dt)\)

  • Draw random number \(r \sim \mathrm{Uniform}(0, 1)\)

  • If \(r < p\):
    • Emit spike

    • Jump STC elements: \(\eta_j \leftarrow \eta_j + q_{\eta_j}\)

    • Jump SFA elements: \(\gamma_i \leftarrow \gamma_i + q_{\gamma_i}\)

    • Set refractory counter: \(r_{\mathrm{count}} \leftarrow \lceil t_{\mathrm{ref}} / dt \rceil\)

If refractory:
  • Decrement refractory counter: \(r_{\mathrm{count}} \leftarrow r_{\mathrm{count}} - 1\)

  • Clamp membrane potential: \(V \leftarrow V_{\mathrm{reset}}\)

Step 4: Buffer External Current

Store \(I_{\mathrm{stim}}(t+dt)\) for use in the next step (NEST ring-buffer semantics: one-step delay).

Differences from gif_psc_exp

Unlike gif_psc_exp which has exactly two fixed synaptic channels (excitatory and inhibitory with tau_syn_ex, tau_syn_in), this model supports an arbitrary number of receptor ports specified by the tau_syn parameter. This enables:

  • Multi-receptor modeling (AMPA, NMDA, GABA_A, GABA_B, etc.)

  • Heterogeneous synaptic time constants within the same neuron

  • Flexible connectivity patterns with receptor-specific routing

All spike weights are applied to the receptor port specified in the connection’s receptor_type field (1-based indexing). Positive or negative weights are both allowed on any receptor.

Parameters:
  • in_size (int, tuple of int) – Shape of the neuron population.

  • g_L (Quantity, ArrayLike, optional) – Leak conductance (nanosiemens). Default: 4.0 nS.

  • E_L (Quantity, ArrayLike, optional) – Leak reversal potential (millivolts). Default: -70.0 mV.

  • C_m (Quantity, ArrayLike, optional) – Membrane capacitance (picofarads). Default: 80.0 pF.

  • V_reset (Quantity, ArrayLike, optional) – Reset potential (millivolts). Default: -55.0 mV.

  • Delta_V (Quantity, ArrayLike, optional) – Voltage scale of stochastic firing (millivolts). Default: 0.5 mV.

  • V_T_star (Quantity, ArrayLike, optional) – Base firing threshold (millivolts). Default: -35.0 mV.

  • lambda_0 (float, optional) – Stochastic firing intensity at threshold (1/s). Default: 1.0 /s.

  • t_ref (Quantity, ArrayLike, optional) – Absolute refractory period (milliseconds). Default: 4.0 ms.

  • tau_syn (sequence of float, optional) – Synaptic time constants (milliseconds), one per receptor port. Specified as bare floats (not Quantities). Default: (2.0,).

  • I_e (Quantity, ArrayLike, optional) – Constant external bias current (picoamperes). Default: 0.0 pA.

  • tau_sfa (sequence of float, optional) – SFA time constants (milliseconds). Default: () (no adaptation).

  • q_sfa (sequence of float, optional) – SFA jump values (millivolts). Default: () (no adaptation).

  • tau_stc (sequence of float, optional) – STC time constants (milliseconds). Default: () (no STC).

  • q_stc (sequence of float, optional) – STC jump values (picoamperes). Default: () (no STC).

  • rng_key (jax.Array, optional) – JAX PRNG key for stochastic spike generation. Default: None.

  • V_initializer (Callable, optional) – Initializer for membrane potential. Default: Constant(-70.0 mV).

  • spk_fun (Callable, optional) – Surrogate gradient function. Default: ReluGrad().

  • spk_reset (str, optional) – Spike reset mode ('hard' or 'soft'). Default: 'hard'.

  • name (str, optional) – Name of the neuron population. Default: None.

State Variables

VHiddenState, shape (*in_size,)

Membrane potential in millivolts.

i_synShortTermState, shape (*in_size, n_receptors)

Synaptic currents in picoamperes.

refractory_step_countShortTermState, shape (*in_size,)

Remaining refractory steps (int).

I_stimShortTermState, shape (*in_size,)

Buffered external current (one-step delay).

last_spike_timeShortTermState, shape (*in_size,)

Time of last spike (milliseconds).

See also

gif_psc_exp

Two-receptor GIF model

iaf_psc_exp_multisynapse

Multi-receptor IAF model without adaptation

References

get_spike(V=None)[source]#

Compute spike output via surrogate gradient function.

init_state(**kwargs)[source]#

Initialize all state variables.

Creates membrane potential, synaptic currents, refractory counters, adaptation elements, buffered current, and internal RNG state.

property n_receptors#

Number of synaptic receptor ports.

update(x=Quantity(0., 'pA'), spike_events=None, receptor_weights=None)[source]#

Update neuron state for one simulation step.

Follows NEST’s gif_psc_exp_multisynapse::update exactly:

  1. Compute pre-decay STC/SFA totals, then decay.

  2. Propagate + decay + inject per-receptor synaptic currents.

  3. If not refractory: exact-propagator membrane update + stochastic spike check; if spiked, jump STC/SFA and set refractory counter. If refractory: decrement counter, clamp V to V_reset.

  4. Buffer external current for next step (one-step delay).

Parameters:
  • x (Quantity, optional) – External current input (pA), buffered by one step. Default: 0 pA.

  • spike_events (iterable or None, optional) – Receptor-indexed spike events. Default: None.

  • receptor_weights (jax.Array or None, optional) – Pre-computed per-receptor weight array, shape v_shape + (n_receptors,). When provided, these weights are added directly to the synaptic currents after decay (same semantics as spike_events). Useful inside brainstate.transform.for_loop where Python-level spike_events iteration is not traceable. Default: None.

Returns:

Binary spike output (float), shape self.V.value.shape.

Return type:

jax.Array