Skip to content

Spike Train Analysis -- 124 Functions (23 Modules)

SC-NeuroCore includes a complete spike train analysis toolkit covering every metric from Elephant, PySpike, SpikeInterface, and NeuroTools. 127 functions across 23 modules (22 spike_stats + 1 explainability). Pure NumPy, zero external dependencies.

Rust acceleration: All 22 spike_stats modules have native Rust implementations with 96 PyO3 bindings (597 tests). See Rust Analysis Engine for the Rust API reference.

Quick Start

Python
from sc_neurocore.analysis import (
    firing_rate, cv_isi, fano_factor, cross_correlation,
    power_spectrum, burst_detection, victor_purpura_distance,
    phase_locking_value, spade_detect, gpfa,
)
import numpy as np

# Generate a Poisson spike train
from sc_neurocore.analysis import homogeneous_poisson
train = homogeneous_poisson(rate_hz=50.0, duration_s=10.0)

# Basic statistics
print(f"Rate: {firing_rate(train):.1f} Hz")
print(f"CV(ISI): {cv_isi(train):.2f}")
print(f"Fano factor: {fano_factor(train):.2f}")

Module Reference

Basic (spike_stats.basic)

Spike extraction, ISI computation, rate, count, binning.

Function Description
spike_times(train, dt) Extract spike times (seconds) from a binary 0/1 array
isi(train, dt) Inter-spike intervals (seconds)
firing_rate(train, dt) Mean firing rate (Hz)
spike_count(train) Total spike count
bin_spike_train(train, bin_size) Bin a binary spike train into spike counts per bin

Variability (spike_stats.variability)

Spike train regularity, complexity, and fractal measures.

Function Description
cv_isi(train, dt) Coefficient of variation of ISI (CV=1 for Poisson, <1 regular)
cv2(train, dt) Local CV2, less sensitive to rate changes (Holt et al. 1996)
local_variation(train, dt) Local variation LV (Shinomoto et al. 2003)
lvr(train, dt, refractoriness_ms) Revised local variation LvR corrected for refractoriness (Shinomoto et al. 2009)
fano_factor(train, window_ms, dt) Fano factor: variance/mean of windowed spike counts
isi_entropy(train, dt, bins) Shannon entropy of ISI distribution (bits)
lempel_ziv_complexity(train) Lempel-Ziv 1976 complexity, normalised by N/log2(N)
approximate_entropy(train, m, r_factor) Approximate entropy ApEn (Pincus 1991)
sample_entropy(train, m, r_factor) Sample entropy SampEn, lower bias (Richman & Moorman 2000)
permutation_entropy(train, order, delay) Bandt-Pompe permutation entropy, normalised to [0,1]
hurst_exponent(train, min_window) Hurst exponent via detrended fluctuation analysis (Peng et al. 1994)
allan_factor(train, dt, n_scales) Allan factor vs window size for fractal clustering detection
rescaled_range(train, min_window) Hurst exponent via R/S analysis (Hurst 1951)
complexity_pdf(train, dt, bins) ISI probability density function (Abeles 1982)
optimal_bin_width(train, dt) Shimazaki-Shinomoto 2007 optimal histogram bin width
optimal_kernel_bandwidth(train, dt) Silverman's rule-of-thumb bandwidth for ISI KDE

Rate Estimation (spike_stats.rate)

Instantaneous and population firing rate estimation.

Function Description
instantaneous_rate(train, dt, kernel, sigma_ms) Kernel-smoothed instantaneous rate (gaussian/exponential/rectangular)
population_rate(trains, dt, sigma_ms) Population-level instantaneous rate across multiple neurons
psth(trials, bin_ms, dt) Peri-stimulus time histogram across trials

Distance Metrics (spike_stats.distance)

Spike train distance and similarity measures.

Function Description
van_rossum_distance(a, b, dt, tau_ms) Van Rossum 2001 exponential-kernel distance
victor_purpura_distance(times_a, times_b, cost_per_s) Victor-Purpura 1996 edit distance
isi_distance(a, b, dt) ISI-distance ratio comparison (Kreuz et al. 2007)
spike_distance(times_a, times_b, t_start, t_end) SPIKE-distance (Kreuz et al. 2013)
spike_sync(times_a, times_b, t_start, t_end) SPIKE-synchronization, normalised to [0,1] (Kreuz et al. 2015)
spike_sync_profile(times_a, times_b, n_bins, ...) Binned SPIKE-synchronization profile
spike_profile(times_a, times_b, n_bins, ...) Binned SPIKE-distance profile
isi_profile(a, b, dt, n_bins) Binned ISI-distance profile
adaptive_spike_distance(times_a, times_b, ...) Adaptive SPIKE-distance with cost interpolation (Kreuz et al. 2013)
schreiber_similarity(a, b, dt, sigma_ms) Smoothed Pearson correlation similarity (Schreiber et al. 2003)
hunter_milton_similarity(times_a, times_b, dt_max) Nearest-neighbour coincidence fraction (Hunter-Milton 2003)
earth_movers_distance(times_a, times_b, ...) EMD between spike time distributions (Rubner et al. 1998)
multi_neuron_victor_purpura(times_list, cost) All-pairs Victor-Purpura distance matrix
generalized_victor_purpura(times_a, times_b, cost_func) Victor-Purpura with arbitrary cost function
spike_distance_matrix(times_list, metric, ...) All-pairs distance matrix (spike_distance/spike_sync/victor_purpura)

Correlation (spike_stats.correlation)

Cross-correlation, synchrony, and covariance measures.

Function Description
cross_correlation(a, b, max_lag_ms, dt) Cross-correlogram between two binary trains
pairwise_correlation(trains, dt) Pairwise Pearson correlation matrix across neurons
event_synchronization(a, b, dt, tau_ms) Quian Quiroga et al. 2002 event synchronization
spike_train_coherence(a, b, dt) Magnitude-squared coherence between spike trains
spike_time_tiling_coefficient(a, b, dt, delta_ms) STTC, corrects for rate bias (Cutts & Eglen 2014)
covariance_matrix(trains, bin_size) Spike count covariance matrix (de la Rocha et al. 2007)
autocorrelation_time(train, dt, max_lag_ms) Autocorrelation time until first zero crossing
noise_correlation(trains, bin_size) Trial-to-trial variability correlation (Averbeck & Lee 2006)
signal_correlation(trains, bin_size) Tuning similarity via Pearson correlation of mean responses
spike_count_covariance(trains, window) Windowed spike count covariance (Kohn & Smith 2005)
joint_psth(a, b, bin_size) Joint PSTH matrix (Aertsen et al. 1989)
coincidence_index(a, b, dt, delta_ms) Rate-corrected coincidence index kappa (Joris et al. 2006)

Spectral (spike_stats.spectral)

Spectral analysis of spike trains.

Function Description
power_spectrum(train, dt) Power spectral density of a binary spike train

Temporal Patterns (spike_stats.temporal)

Burst detection, latency, onset, and change point analysis.

Function Description
burst_detection(train, dt, max_isi_ms, min_spikes) Detect bursts as consecutive short-ISI spikes
first_spike_latency(train, dt) Time to first spike (seconds)
response_onset(train, baseline_steps, dt, threshold_sigma) Detect response onset exceeding baseline + threshold
change_point_detection(train, bin_size, threshold) CUSUM-based firing rate change points (Page 1954)

Stimulus (spike_stats.stimulus)

Spike-triggered analysis and receptive field estimation.

Function Description
spike_triggered_average(stimulus, train, window_steps) STA: average stimulus preceding each spike
spike_triggered_covariance(stimulus, train, window_steps) STC: covariance of pre-spike stimulus (Schwartz et al. 2006)
spatial_information(train, positions, n_bins, dt) Spatial information in bits/spike (Skaggs et al. 1993)
place_field_detection(train, positions, ...) Detect place fields (O'Keefe & Dostrovsky 1971)
tuning_curve(train, stimulus_values, n_bins, dt) Firing rate vs stimulus value (Dayan & Abbott 2001)

LFP Coupling (spike_stats.lfp)

Spike-LFP phase locking, coherence, and phase histograms.

Function Description
phase_locking_value(train, lfp) PLV via Hilbert phase at spike times
spike_field_coherence(train, lfp, dt) Spike-field coherence SFC in frequency domain
spike_phase_histogram(train, lfp, n_bins) Histogram of LFP phase at spike times

Surrogates (spike_stats.surrogates)

Surrogate spike train generation for significance testing.

Function Description
surrogate_isi_shuffle(train, seed) ISI-shuffled surrogate preserving rate + ISI distribution
surrogate_dither(train, dither_ms, dt, seed) Spike jittering surrogate (+/- dither window)
surrogate_trial_shuffle(trains, seed) Trial-order shuffling destroying trial-to-trial correlation
homogeneous_poisson(rate_hz, duration_s, dt, seed) Generate homogeneous Poisson spike train
inhomogeneous_poisson(rate_func, duration_s, dt, seed) Time-varying Poisson via thinning (Lewis & Shedler 1979)
gamma_process(rate_hz, shape, duration_s, dt, seed) Gamma-renewal process (shape=1 Poisson, >1 regular)
compound_poisson_process(rate_hz, burst_mean, ...) Compound Poisson with burst events (Snyder & Miller 1991)
surrogate_joint_isi(train, seed) Joint-ISI surrogate preserving serial correlations (Louis et al. 2010)
surrogate_bin_shuffling(train, bin_size, seed) Within-bin spike shuffling (Hatsopoulos et al. 2003)
surrogate_spike_train_shifting(train, max_shift, seed) Circular shifting surrogate

Information Theory (spike_stats.information)

Information-theoretic measures for spike trains.

Function Description
mutual_information(a, b, bin_size) Mutual information between binned spike trains (bits)
transfer_entropy(source, target, bin_size, lag) Transfer entropy from source to target (bits)
spike_train_entropy(train, bin_size, word_length) Binary word entropy (Strong et al. 1998)
noise_entropy(train, n_trials, bin_size, word_length) Noise entropy via pseudo-trials (de Ruyter van Steveninck et al. 1997)
stimulus_specific_information(counts, stim_ids) SSI in bits (Butts 2003)
kozachenko_leonenko_mi(x, y, k) k-NN mutual information estimator in nats (Kraskov et al. 2004)
time_rescaling_ks_test(times, rate_func, ...) KS goodness-of-fit for point processes (Brown et al. 2002)

Causality (spike_stats.causality)

Granger causality and directed connectivity.

Function Description
pairwise_granger_causality(source, target, ...) Pairwise Granger causality log-likelihood ratio (Granger 1969)
conditional_granger_causality(source, target, cond, ...) Conditional GC controlling for a third signal (Geweke 1984)
spectral_granger_causality(trains, bin_size, order, ...) Frequency-domain GC via VAR model (Geweke 1982)
partial_directed_coherence(trains, ...) PDC: normalised directed connectivity (Baccala & Sameshima 2001)
directed_transfer_function(trains, ...) DTF: normalised transfer function (Kaminski & Blinowska 1991)

Dimensionality Reduction (spike_stats.dimensionality)

Low-dimensional projections of population activity.

Function Description
spike_train_pca(trains, n_components, bin_size, backend) PCA on binned spike count matrix
demixed_pca(trains_by_condition, n_components, ..., backend) Demixed PCA separating condition variance (Kobak et al. 2016)
factor_analysis(trains, n_factors, bin_size, n_iter, backend) Factor analysis via EM (Rubin & Thayer 1982)

Deterministic eigendecomposition. The covariance eigendecomposition returns eigenvalues in descending order with sign-canonicalised eigenvectors (each component's largest-magnitude entry is positive), so the projections are reproducible. Factor analysis starts from a deterministic PCA initialisation (replacing a random one — seed-independent, like the GPFA init) and solves its symmetric positive-definite M and E[zzᵀ] systems by Cholesky rather than an explicit inverse (the Rust backend previously used a hand-rolled Jacobi sweep and a Gauss-Jordan inverse).

Polyglot chain. Each estimator accepts backend= over five parity-verified backends (NumPy / Rust / Julia / Go / Mojo), agreeing to ~1e-13: LAPACK in NumPy and Julia, the nalgebra symmetric solver in Rust, and an accurate cyclic-Jacobi solver where no LAPACK is linked (Go / Mojo). Unlike the smaller structured kernels, dense symmetric eigendecomposition is LAPACK's strength, so on the reference workload (benchmarks/bench_dimensionality.py, i5-11600K, shielded cores) the NumPy/LAPACK reference is the fastest path (Rust ~0.5×, Mojo ~0.12×, Go ~0.07×, Julia interop-bound). backend="auto" therefore resolves to the NumPy reference; the compiled backends are kept for cross-language parity and for deployments that run without an optimised BLAS.

Decoding (spike_stats.decoding)

Neural population decoding algorithms.

Function Description
population_vector_decode(trains, directions, window) Georgopoulos population vector decoding
bayesian_decode(counts, tuning_rates, prior) Bayesian MAP decoder (Dayan & Abbott 2001)
maximum_likelihood_decode(counts, tuning_rates) Maximum likelihood Poisson decoder
linear_discriminant_decode(data, labels, test) Fisher LDA decoder (Fisher 1936)
naive_bayes_decode(data, labels, test) Gaussian naive Bayes decoder

Network (spike_stats.network)

Network-level analysis: connectivity, assemblies, synfire chains.

Function Description
functional_connectivity(trains, max_lag_ms, dt) Infer connectivity from peak cross-correlation
unitary_events(trains, bin_size, alpha) Detect significant synchronous bins (Gruen et al. 2002)
cell_assembly_detection(trains, bin_size, threshold) PCA-based cell assembly detection (Lopes-dos-Santos et al. 2013)
synfire_chain_detection(trains, dt, max_delay_ms, ...) Cross-correlation peak ordering (Abeles 1991)

Point Process (spike_stats.point_process)

Point process models and hazard functions.

Function Description
conditional_intensity(train, dt, window_ms) Moving-window MLE conditional intensity (Brown et al. 2004)
isi_hazard_function(train, dt, bins) ISI hazard function h(t) = f(t)/S(t) (Tuckwell 1988)
isi_survivor_function(train, dt, bins) ISI survivor function S(t) = P(ISI > t)
renewal_density(train, dt, bins) Renewal density normalised by mean rate (Cox 1962)

Sorting Quality (spike_stats.sorting_quality)

Spike sorting quality metrics.

Function Description
isolation_distance(cluster, noise, backend) Mahalanobis isolation distance (Harris et al. 2001)
l_ratio(cluster, noise, backend) L-ratio cluster quality (Schmitzer-Torbert et al. 2005)
silhouette_score(features, labels) Mean silhouette score (Rousseeuw 1987)
d_prime(cluster_a, cluster_b) Sensitivity index between two clusters (Green & Swets 1966)
isi_violation_rate(train, dt, refractory_ms) Fraction of ISIs below refractory period (Hill et al. 2011)
presence_ratio(train, n_bins) Fraction of time bins with at least one spike (IBL 2019)
amplitude_cutoff(amplitudes, bins) Estimated missing spike fraction (Hill et al. 2011)
snr(waveforms) Signal-to-noise ratio of spike waveforms (Suner et al. 2005)
nn_hit_rate(cluster, noise, k) k-NN cluster purity (Chung et al. 2017)
drift_metric(waveforms, timestamps, n_bins) Waveform amplitude drift over time (IBL 2019)

Mahalanobis kernel. isolation_distance and l_ratio share one numerically optimal kernel for the squared Mahalanobis distance (x-μ)ᵀ Σ⁻¹ (x-μ). The regularised cluster covariance Σ = L Lᵀ is Cholesky- factorised once and the quadratic form is obtained by a triangular solve L z = x-μ followed by Σ z² — the covariance is never inverted explicitly, which is both more accurate for ill-conditioned cluster covariances and cheaper than forming Σ⁻¹ and multiplying.

Polyglot chain. isolation_distance(..., backend=...) and l_ratio(..., backend=...) run the same Cholesky kernel across five backends (NumPy / Rust / Julia / Go / Mojo), agreeing with the NumPy reference to floating-point round-off (~1e-13). backend="auto" prefers the Rust engine (the always-available compiled path) and otherwise falls back to the NumPy reference; "python", "rust", "julia", "go" and "mojo" force a specific path. On the reference workload (benchmarks/bench_sorting_quality.py, i5-11600K, shielded cores 10–11; 64-point cluster, 256 noise points, 12 features) the compiled backends beat NumPy — Mojo ~4.6×, Go ~3.8×, Rust ~1.9× — while the Julia path is dominated by per-call interop overhead on this small workload (~0.5×). Degenerate inputs (n_cluster < 2, fewer noise points than the cluster size for the isolation distance, or empty noise for the L-ratio) return nan before any backend runs.

Waveform (spike_stats.waveform)

Spike waveform shape analysis.

Function Description
waveform_width(waveform, dt) Trough-to-peak width in seconds (Bartho et al. 2004)
waveform_amplitude(waveform) Peak-to-trough amplitude
waveform_repolarization_slope(waveform, dt) Max dV/dt after trough (Bean 2007)
waveform_recovery_slope(waveform, dt) dV/dt during return to baseline (Bean 2007)
waveform_halfwidth(waveform, dt) Duration at half-minimum amplitude (Bartho et al. 2004)
waveform_pt_ratio(waveform) Peak-to-trough ratio (Bartho et al. 2004)

Statistics (spike_stats.statistics)

Significance testing.

Function Description
significance_bootstrap(func, a, b, n_surrogates, seed) Bootstrap permutation test for pairwise statistics

Patterns (spike_stats.patterns)

Spike directionality, ordering, and higher-order patterns.

Function Description
spike_directionality(times_a, times_b, ...) Asymmetry in [-1,1]: positive means A leads B (Kreuz et al. 2015)
spike_train_order(times_list, ...) Pairwise directionality matrix (Kreuz et al. 2017)
cubic_higher_order(train, dt, max_lag) Third-order cumulant C3(tau1, tau2) (Nikias & Petropulu 1993)

SPADE (spike_stats.spade)

Spike Pattern Detection and Evaluation (Torre et al. 2013).

Function Description
spade_detect(trains, bin_ms, dt, min_support, ...) Detect significant spatiotemporal spike patterns via frequent itemset mining + surrogate testing

GPFA (spike_stats.gpfa)

Gaussian Process Factor Analysis (Yu et al. 2009). Deterministic PCA initialisation and a five-language EM chain (NumPy / Rust / Julia / Go / Mojo) that agree to floating-point round-off. See GPFA -- deterministic init and polyglot EM for the algorithm, the backend contract and the benchmark.

Function Description
gpfa(trains, n_latents, bin_ms, dt, max_iter, ..., backend) Extract smooth latent trajectories via EM with SE-GP priors
gpfa_transform(new_trains, params, bin_ms, dt) Project new data using learned GPFA parameters
gpfa_pca_init(Y, n_latents, bin_ms) Deterministic PCA initialisation shared by every backend

Explainability

sc_neurocore.analysis.explainability

Explain spike-vector activity through a configured neuron-to-concept map.

SpikeToConceptMapper

Map spike-vector activity to human-readable semantic concepts.

Source code in src/sc_neurocore/analysis/explainability.py
Python
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
class SpikeToConceptMapper:
    """Map spike-vector activity to human-readable semantic concepts."""

    def __init__(self, concept_map: Dict[int, str]):
        self.concept_map = concept_map

    def explain(self, spikes: np.ndarray[Any, Any]) -> str:
        """Describe the concepts implied by an active spike vector.

        Parameters
        ----------
        spikes : numpy.ndarray of shape (n_neurons,)
            Spike activity; indices with a value greater than zero are
            treated as active.

        Returns
        -------
        str
            A human-readable sentence naming the active concepts.
        """
        active_indices = np.where(spikes > 0)[0]

        concepts = []
        for idx in active_indices:
            if idx in self.concept_map:
                concepts.append(self.concept_map[idx])
            else:
                concepts.append(f"Unknown({idx})")

        if not concepts:
            return "The agent is idle."

        return f"The agent is active on: {', '.join(concepts)}"

explain(spikes)

Describe the concepts implied by an active spike vector.

Parameters

spikes : numpy.ndarray of shape (n_neurons,) Spike activity; indices with a value greater than zero are treated as active.

Returns

str A human-readable sentence naming the active concepts.

Source code in src/sc_neurocore/analysis/explainability.py
Python
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
def explain(self, spikes: np.ndarray[Any, Any]) -> str:
    """Describe the concepts implied by an active spike vector.

    Parameters
    ----------
    spikes : numpy.ndarray of shape (n_neurons,)
        Spike activity; indices with a value greater than zero are
        treated as active.

    Returns
    -------
    str
        A human-readable sentence naming the active concepts.
    """
    active_indices = np.where(spikes > 0)[0]

    concepts = []
    for idx in active_indices:
        if idx in self.concept_map:
            concepts.append(self.concept_map[idx])
        else:
            concepts.append(f"Unknown({idx})")

    if not concepts:
        return "The agent is idle."

    return f"The agent is active on: {', '.join(concepts)}"

Integrated Information (Phi*)

phi_star(...) estimates geometric integrated information following Barrett and Seth (2011). It compares Gaussian mutual information between past and future whole-system states against contiguous bipartitions and returns a non-negative reducibility estimate in nats. This is a tractable analysis metric, not a claim about consciousness or intrinsic causal power.

Each Gaussian mutual information is a difference of covariance log-determinants taken from Cholesky factors (MI = 0.5 (log|Cov_X| + log|Cov_Y| - log|Cov_XY|)). Summing log-determinants is the numerically stable form of the determinant ratio: the naive product of raw determinants underflows for larger channel counts, where the log-determinant form stays exact.

phi_from_spike_trains(...) bins binary spike trains into spike counts and then applies phi_star(...) at the requested lag. The estimator is suitable for small analysis windows and coarse-grained spike-train diagnostics; it is not a full IIT minimum-information-partition search.

Polyglot chain. phi_star(..., backend=...) runs the same estimator across five backends (NumPy / Rust / Julia / Go / Mojo), agreeing to floating-point round-off (Rust, Julia, Go ~1e-15; Mojo ~1e-10). backend="auto" prefers the Rust engine when present, otherwise the NumPy reference. On the reference workload (benchmarks/bench_phi.py, i5-11600K, shielded cores) every compiled backend beats NumPy: Rust ~7x, Julia ~4.4x, Mojo ~3.5x, Go ~3.0x.

The public contract is tested as follows:

  • independent continuous channels produce near-zero Phi* within finite-sample tolerance;
  • correlated channels produce positive Phi*;
  • two-channel results are invariant to channel ordering;
  • single-channel and too-short inputs return 0.0;
  • Phi* is always non-negative;
  • correlated spike trains pass through the binning adapter;
  • independent random spike trains remain low-Phi under the maintained bound;
  • the Rust, Julia, Go and Mojo backends match the NumPy reference (gated parity tests).

sc_neurocore.analysis.phi_estimation.phi_star(data, tau=1, backend='auto')

Geometric integrated information Phi* (Barrett & Seth 2011).

Phi* = MI(past; future) - min_partition Σ_k MI(past_k; future_k) under the Gaussian assumption, with each mutual information a difference of covariance log-determinants (Cholesky form).

Parameters

data : numpy.ndarray Shape (n_channels, n_timesteps) — spike counts or continuous signals. tau : int, optional Time lag for the past→future mapping. backend : str, optional "auto" selects the fastest available backend (Rust engine when present, otherwise the NumPy reference); "python", "rust", "julia", "go" and "mojo" force a specific path.

Returns

float Phi* estimate in nats. Non-negative; 0 means fully reducible.

Source code in src/sc_neurocore/analysis/phi_estimation.py
Python
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
def phi_star(data: np.ndarray[Any, Any], tau: int = 1, backend: str = "auto") -> float:
    """Geometric integrated information Phi* (Barrett & Seth 2011).

    ``Phi* = MI(past; future) - min_partition Σ_k MI(past_k; future_k)`` under the
    Gaussian assumption, with each mutual information a difference of covariance
    log-determinants (Cholesky form).

    Parameters
    ----------
    data : numpy.ndarray
        Shape ``(n_channels, n_timesteps)`` — spike counts or continuous signals.
    tau : int, optional
        Time lag for the past→future mapping.
    backend : str, optional
        ``"auto"`` selects the fastest available backend (Rust engine when present,
        otherwise the NumPy reference); ``"python"``, ``"rust"``, ``"julia"``,
        ``"go"`` and ``"mojo"`` force a specific path.

    Returns
    -------
    float
        Phi* estimate in nats. Non-negative; ``0`` means fully reducible.
    """
    arr = np.ascontiguousarray(data, dtype=np.float64)
    n, n_timesteps = arr.shape
    if n < 2 or 2 * tau >= n_timesteps:
        return 0.0
    return _phi_star_dispatch(arr, int(tau), backend)

sc_neurocore.analysis.phi_estimation.phi_from_spike_trains(spikes, bin_size=10, tau=1, backend='auto')

Compute Phi* from binary spike trains by binning into spike counts.

Parameters

spikes : numpy.ndarray Shape (n_neurons, n_timesteps), binary {0, 1}. bin_size : int, optional Number of timesteps per bin. tau : int, optional Time lag in bins. backend : str, optional Forwarded to :func:phi_star.

Returns

float Phi* in nats.

Source code in src/sc_neurocore/analysis/phi_estimation.py
Python
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
def phi_from_spike_trains(
    spikes: np.ndarray[Any, Any], bin_size: int = 10, tau: int = 1, backend: str = "auto"
) -> float:
    """Compute Phi* from binary spike trains by binning into spike counts.

    Parameters
    ----------
    spikes : numpy.ndarray
        Shape ``(n_neurons, n_timesteps)``, binary ``{0, 1}``.
    bin_size : int, optional
        Number of timesteps per bin.
    tau : int, optional
        Time lag in bins.
    backend : str, optional
        Forwarded to :func:`phi_star`.

    Returns
    -------
    float
        Phi* in nats.
    """
    n_neurons, n_steps = spikes.shape
    n_bins = n_steps // bin_size
    if n_bins < 2 * tau + 2:
        return 0.0

    binned = np.zeros((n_neurons, n_bins), dtype=np.float64)
    for b in range(n_bins):
        binned[:, b] = spikes[:, b * bin_size : (b + 1) * bin_size].sum(axis=1)

    return phi_star(binned, tau=tau, backend=backend)