correlospinmatrix_detector#
- class brainpy.state.correlospinmatrix_detector(in_size=1, delta_tau=None, tau_max=None, Tstart=Quantity(0., 'ms'), Tstop=None, N_channels=1, start=Quantity(0., 'ms'), stop=None, origin=Quantity(0., 'ms'), name=None)#
NEST-compatible
correlospinmatrix_detectordevice.1. Overview
correlospinmatrix_detectorreceives binary-state spike streams from multiple receptor channels and accumulates raw auto/cross covariance histograms over negative, zero, and positive lags. It mirrors NESTmodels/correlospinmatrix_detector.{h,cpp}for event decoding, pulse finalization, and lag-bin accumulation.2. Binary-State Decoding and Pulse Construction
For receptor channel \(c\), define a binary state \(x_c(t)\in\{0,1\}\) on integer simulation steps. Runtime events are triples \(e=(c, t, m)\), where \(m\) is multiplicity.
Decoding rule (NEST compatible):
\(m=1\) — mark a tentative down-transition.
A second event with identical
(channel, stamp_step)or \(m=2\): confirm up-transition (\(x_c\leftarrow 1\)) and cancel tentative-down handling for that event pair.
A covariance update is triggered only when a previous tentative down-transition becomes confirmed. The finalized pulse is \(p_i=(i, t_i^{\mathrm{on}}, t_i^{\mathrm{off}})\), where \(t_i^{\mathrm{on}}\) is taken from
_last_change[i]and \(t_i^{\mathrm{off}}\) from the confirmed down-transition stamp.3. Lag-Bin Accumulation Equations
Let \(\Delta=\Delta_{\tau,\mathrm{steps}}\), \(H=\tau_{\max,\mathrm{steps}}/\Delta\), and \(k_0=H\) (zero-lag bin index). For each finalized pulse \(p_i\), iterate retained history pulses \(p_j=(j, t_j^{\mathrm{on}}, t_j^{\mathrm{off}})\).
Integer lag offsets are constrained by
\[\delta_{\min}=\max\!\bigl(t_j^{\mathrm{on}}-t_i^{\mathrm{off}}, -\tau_{\max,\mathrm{steps}}\bigr),\qquad \delta_{\max}=\min\!\bigl(t_j^{\mathrm{off}}-t_i^{\mathrm{on}}, \tau_{\max,\mathrm{steps}}\bigr).\]For an offset \(\delta\), overlap length in simulation steps is
\[L_{ij}(\delta)= \min\!\bigl(t_i^{\mathrm{off}},\; t_j^{\mathrm{off}}-\delta\Delta\bigr) -\max\!\bigl(t_i^{\mathrm{on}},\; t_j^{\mathrm{on}}-\delta\Delta\bigr).\]If \(L_{ij}(\delta)>0\), add this integer duration to
count_covariancebins:Zero lag (\(\delta=0\)): update
(i, j, k_0)and, when \(i\neq j\), the mirrored entry(j, i, k_0).Negative offsets (\(\delta<0\)): update both mirrored bins
(i, j, k_0-\delta)and(j, i, k_0+\delta).Positive offsets (\(\delta>0\)): update mirrored bins only for \(i\neq j\), matching NEST triangular-edge conventions.
count_covariancehas shape(N_channels, N_channels, N_bins)with\[N_{\mathrm{bins}} = 1 + 2\,\frac{\tau_{\max,\mathrm{steps}}} {\Delta_{\tau,\mathrm{steps}}},\]and stores overlap lengths in simulation-step units (not milliseconds).
4. Windowing, Assumptions, and Constraints
Activity filtering follows the half-open interval
(origin + start, origin + stop]in step space. Events outside this interval are discarded before decoding.TstartandTstopare validated and included in calibration signatures for reset behavior, but they do not gate accumulation inupdate(), matching current NEST source behavior.Calibration constraints:
dt > 0.start,stop(if finite),origin,delta_tau, andtau_maxmust each align exactly to integer multiples ofdt.delta_taumust be finite and strictly positive.tau_maxmust be finite, non-negative, and divisible bydelta_tau.N_channels >= 1; runtime receptor IDs must be in[0, N_channels - 1].
5. Computational Implications
For each accepted event, down-transition handling is constant-time, while pulse insertion and pulse-to-history correlation are linear in the retained queue length \(Q\). Memory scales as \(O\!\left(Q + N_{\mathrm{channels}}^2 N_{\mathrm{bins}}\right)\). Queue pruning uses NEST minimum-delay semantics with
min_delay_steps = 1.- Parameters:
in_size (
Size, optional) – Output size/shape metadata used bybrainstate.nn.Dynamics. The detector is event-driven and stores internal tensors, soin_sizedoes not changecount_covarianceshape. Default is1.delta_tau (
quantity (ms)orfloatorNone, optional) – Lag-bin width \(\Delta_\tau\). Unitfulsaiunitquantities are accepted and converted to ms; bare floats are interpreted as ms. Must be finite, strictly positive, and an integer multiple of simulationdt.Noneauto-selectsdt. Default isNone.tau_max (
quantity (ms)orfloatorNone, optional) – One-sided lag horizon \(\tau_{\max}\). Unitful quantities accepted. Must be finite, non-negative, an integer multiple ofdt, and an exact integer multiple ofdelta_tau.Noneauto-selects10 * delta_tau. Default isNone.Tstart (
quantity (ms)orfloat, optional) – Non-negative scalar lower time bound in ms retained for NEST API compatibility. Participates in calibration signature and triggers a state reset when changed. Default is0.0 * u.ms.Tstop (
quantity (ms)orfloatorNone, optional) – Non-negative scalar upper time bound in ms retained for NEST API compatibility.Nonemeans \(+\infty\). Participates in calibration signature and triggers a state reset when changed. Default isNone.N_channels (
intorArrayLike, optional) – Number of receptor channels. Must resolve to a scalar integer>= 1. Runtime channel IDs must be in[0, N_channels - 1]. Default is1.start (
quantity (ms)orfloat, optional) – Exclusive lower bound of the activity window relative tooriginin ms. Must be scalar-convertible and aligned to simulationdt. Default is0.0 * u.ms.stop (
quantity (ms)orfloatorNone, optional) – Inclusive upper bound of the activity window relative tooriginin ms. Must be scalar-convertible and aligned todtwhen finite.Nonemeans \(+\infty\). Default isNone.origin (
quantity (ms)orfloat, optional) – Activity-window origin shift in ms. The effective activity window becomes(origin + start, origin + stop]. Must be scalar-convertible and aligned todt. Default is0.0 * u.ms.name (
strorNone, optional) – Optional node name forwarded tobrainstate.nn.Dynamics. IfNone, a name is auto-generated. Default isNone.
Parameter Mapping
Parameter
Default
Math symbol
Semantics
delta_tauNone→dt\(\Delta_\tau\)
Lag-bin width; auto-resolved to simulation
dtwhen omitted.tau_maxNone→10 * delta_tau\(\tau_{\max}\)
One-sided lag horizon; auto-resolved when omitted.
Tstart0.0 ms\(T_{\mathrm{start}}\)
Calibration/reset compatibility parameter (not a runtime gate).
TstopNone(\(+\infty\))\(T_{\mathrm{stop}}\)
Calibration/reset compatibility parameter (not a runtime gate).
N_channels1\(N_{\mathrm{channels}}\)
Number of receptor channels and covariance matrix axes.
start0.0 ms\(t_{\mathrm{start,rel}}\)
Relative exclusive lower bound of the activity window.
stopNone(\(+\infty\))\(t_{\mathrm{stop,rel}}\)
Relative inclusive upper bound of the activity window.
origin0.0 ms\(t_0\)
Global shift applied to
startandstopboundaries.- Raises:
ValueError – If scalar parameters are non-scalar, non-finite where finite values are required, misaligned to simulation resolution, or violate constraints (e.g.
tau_max % delta_tau != 0,stop < start,N_channels < 1, invalid runtime receptor IDs, negative multiplicities, non-finitespikes, or mismatched event-array sizes).KeyError – If runtime environment keys such as simulation time
't'ordtare unavailable during calibration or update.
Notes
Connection delays and weights are ignored, matching NEST.
Runtime events are provided through
update()arrays (spikes,receptor_ports/receptor_types,multiplicities,stamp_steps), each scalar-broadcastable to one event axis.Optional
multiplicitiesemulate NESTSpikeEventmultiplicity.History pruning uses NEST minimum-delay semantics with
min_delay_steps = 1.Calibration is cached and reused across steps; it is automatically invalidated if
dtor any window parameter changes between calls.
Examples
Two-channel detector with explicit events:
>>> import brainpy >>> import brainstate >>> import saiunit as u >>> import numpy as np >>> with brainstate.environ.context(dt=0.1 * u.ms): ... det = brainpy.state.correlospinmatrix_detector( ... N_channels=2, ... delta_tau=1.0 * u.ms, ... tau_max=3.0 * u.ms, ... ) ... with brainstate.environ.context(t=0.0 * u.ms): ... det.update( ... spikes=np.array([1.0, 1.0]), ... receptor_ports=np.array([0, 0]), ... multiplicities=np.array([1, 1]), ... stamp_steps=np.array([1, 1]), ... ) ... out = det.flush() >>> out['count_covariance'].shape (2, 2, 7)
Default parameters with no input events and explicit state reset:
>>> import brainpy >>> import brainstate >>> import saiunit as u >>> with brainstate.environ.context(dt=0.1 * u.ms): ... det = brainpy.state.correlospinmatrix_detector() ... with brainstate.environ.context(t=0.0 * u.ms): ... _ = det.update() # no events; returns current state ... det.init_state() # explicit reset
References
- property count_covariance: ndarray#
Return accumulated raw covariance histogram.
- Returns:
int64tensor with shape(N_channels, N_channels, N_bins). Entries are accumulated overlap durations measured in simulation steps.- Return type:
np.ndarray
- flush()[source]#
Return current detector outputs without mutating state.
- Returns:
Mapping with one key,
'count_covariance', containing the currentint64covariance tensor.- Return type:
dict[str,np.ndarray]
- get(key='count_covariance')[source]#
Read a detector attribute using NEST-style string keys.
- Parameters:
key (
str, optional) – Attribute name. Supported values are'count_covariance','delta_tau','tau_max','Tstart','Tstop','N_channels','start','stop', and'origin'. Default is'count_covariance'.- Returns:
out – Requested value. Time-valued scalars are returned in milliseconds,
count_covarianceis returned asnp.ndarray[int64].- Return type:
- Raises:
KeyError – If
keyis unsupported.ValueError – If stored parameter values fail scalar/unit conversion checks.
- update(spikes=None, receptor_ports=None, receptor_types=None, multiplicities=None, stamp_steps=None)[source]#
Process one simulation tick worth of incoming events.
- Parameters:
spikes (
ArrayLikeorNone, optional) – Event-presence values for this call. Scalar or 1-D array of shape(n_events,). Values<= 0are ignored. Ifmultiplicities is None, integer-like positive values are used as multiplicities; otherwise positive entries act as an event mask.Nonemeans no new events.receptor_ports (
ArrayLikeorNone, optional) – Receptor channel IDs, scalar-broadcastable or shape(n_events,). Required when events target channels other than0. Each value must be an integer in[0, N_channels - 1].receptor_types (
ArrayLikeorNone, optional) – Alias ofreceptor_portsfor NEST naming compatibility. Used only whenreceptor_ports is None.multiplicities (
ArrayLikeorNone, optional) – Non-negative integer multiplicities, scalar-broadcastable or shape(n_events,). If provided, effective multiplicity ismultiplicities[i]for positivespikes[i]and0otherwise.Nonetriggers multiplicity inference fromspikes.stamp_steps (
ArrayLikeorNone, optional) – Integer simulation stamps (1-based step count), scalar-broadcastable or shape(n_events,).Noneusescurrent_step + 1for all events.
- Returns:
out – Mapping
{'count_covariance': ndarray}, where the ndarray isint64with shape(N_channels, N_channels, N_bins).- Return type:
jax.Array- Raises:
ValueError – If runtime arrays are non-finite, negative where forbidden (for example
multiplicities), size-incompatible, or contain unknown receptor channels.KeyError – If simulation time
't'ordtis unavailable inbrainstate.environ.