Skip to main content

spdal

Single-Pass Discard-After-Learn — hyperellipsoid classifiers for online streaming data.

Each training sample is processed once and then discarded. No full dataset is ever stored. All classifiers implement scikit-learn's partial_fit / predict interface.


Installation

pip install spdal

Development mode:

git clone https://github.com/PeemapatW/single-pass-discard-after-learn
cd single-pass-discard-after-learn
pip install -e ".[dev]"

Quick Start

from sklearn.datasets import make_classification
from spdal import LRHE

X, y = make_classification(n_samples=500, random_state=42)

clf = LRHE()
clf.fit(X[:400], y[:400])
print(clf.predict(X[400:]))          # array of class labels
print(len(clf.neuron_list))          # number of learned prototypes

Incremental learning

from spdal import TRACED
import numpy as np

X, y = make_classification(n_samples=500, random_state=42)
classes = np.unique(y)

clf = TRACED()
for i in range(0, 400, 50):
    clf.partial_fit(X[i:i+50], y[i:i+50], classes=classes)

print(clf.predict(X[400:]))

Classifiers

Class Full name Year
VEBF Versatile Elliptic Basis Function 2010
SCIL Streaming Chunk Incremental Learning 2019
LRHE Learning with Recoil in Hyperellipsoidal Structure 2020
SHEF Scalable Hyper-Ellipsoidal Function 2020
D4 Diversion of Data Distribution Direction 2026
TRACED Trend-Adaptive Classification with Ellipsoidal Disambiguation 2026

Comparison

Feature VEBF SCIL LRHE SHEF D4 TRACED
Learning mode Single Chunk Single Single Chunk Chunk
Neurons per class Multiple Multiple Multiple Multiple One Multiple
Width formula Init: avg pairwise dist; Update: width + center shift; Merge: sqrt(2π|λ|) Update: width + center shift; Expand: sqrt(1+η·max_psi)·w; Merge: 1.96 sqrt(|λ|/n) Init: avg pairwise dist; Update: width + center shift; Merge: sqrt(2π|λ|) Update: recursive covariance; Width = r·sqrt(λ) Init: avg pairwise dist; Update: α·sqrt(2πλ) + (1-α)·(width + center shift) Init: mean NN dist; Update: γ·r·sqrt(λ) + (1-γ)·(width + center shift); Merge: r·sqrt(λ)
Creation threshold Hyperellipsoidal test Hyperellipsoidal test Hyperellipsoidal test Euclidean distance (dynamic threshold) N/A (always merges) Euclidean distance (dynamic threshold)
Ambiguity resolution — — Shift-and-shrink Discriminant projection Coincident: principal-axis subspace Coincident: principal-axis subspace; Exterior: EMA displacement + expansion

Parameters

VEBF

from spdal import VEBF
clf = VEBF(theta=0, delta=1)
Parameter Default Description
theta 0 Overlap threshold for neuron merging
delta 1 Width scaling from pairwise distances for initial width [$\delta > 0$]

SCIL

from spdal import SCIL
clf = SCIL(N0=3, eta=2, delta=1, theta=0)
Parameter Default Description
N0 3 Min samples for an active neuron in prediction
eta 2 Width expansion scaling factor
delta 1 Width scaling from pairwise distances for initial width [$\delta > 0$]
theta 0 Overlap threshold for neuron merging

LRHE

from spdal import LRHE
clf = LRHE(alpha=0.99, theta=0, delta=1)
Parameter Default Description
alpha 0.99 Shrink multiplier during recoil [$\alpha \in [0,1]$]; paper-recommended (gradual shrinking)
theta 0 Overlap threshold for neuron merging
delta 1 Width scaling from pairwise distances for initial width [$\delta > 0$]

SHEF

from spdal import SHEF
clf = SHEF(M=3, r=1.5)
Parameter Default Description
M 3 Min samples before adaptive threshold triggers
r 1.5 Ellipsoid radius scaling constant [$r > 0$]

D4

from spdal import D4
clf = D4(width_parameter=1, reduce_dims=0, delta=1, norm=2, r=1.5, threshold=15)
Parameter Default Description
width_parameter 1 Blend: 1 = pure statistical width, 0 = pure expansion-based [$\text{width_parameter} \in [0,1]$]
reduce_dims 0 Axes to drop in coincident-region disambiguation
delta 1 Width scaling from pairwise distances for initial width [$\delta > 0$]
norm 2 Lp norm for distance calculation
r 1.5 Statistical ellipsoid radius width scaling factor [$r > 0$]
threshold 15 Angle threshold (degrees) for axis pairing

D4 maintains one neuron per class. When two nearest neurons belong to different classes, it select their axes using parallel and compactness criteria and assigns the class with the smaller projected distance in that subspace.

Note: Theorem 2 of the D4 paper contains a sign error in the proof. This does not affect the algorithm or experimental results. See technical note for details.

TRACED

from spdal import TRACED
clf = TRACED(
    alpha=0.5, beta=0.01, delta=2, width_parameter=1,
    reduce_dims=1, N0=3, r=2.507, norm=2,
    method='overlap-outside', distance_metric='boundary',threshold=15
)
Parameter Default Description
alpha 0.5 EMA weight for displacement smoothing (0 = disabled) [$\alpha \in [0,1]$]
beta 0.01 EMA weight for expansion-rate smoothing (0 = disabled) [$\beta \in [0,1]$]
delta 2 Initial dynamic threshold scaling (mean NN distance × delta) [$\delta > 0$]
width_parameter 1 Blend: 1 = pure statistical width, 0 = pure expansion-based [$\text{width_parameter} \in [0,1]$]
reduce_dims 1 Axes to drop in coincident-region disambiguation
N0 3 Min samples for an active neuron in prediction and adaptive threshold triggers
r sqrt(2π) Statistical ellipsoid radius width scaling factor [$r > 0$]
norm 2 Lp norm for distance calculation
method 'overlap-outside' Corrections to apply: 'overlap', 'outside', or both
distance_metric 'boundary' 'boundary' or 'center'
threshold 15 Angle threshold (degrees) for axis pairing

TRACED resolves two ambiguous regions:

  • Coincident (x inside multiple classes) — principal-axis subspace projection (like D4)
  • Exterior (x outside all neurons) — predicts using EMA-smoothed displacement and expansion as a trend model

sklearn Interface

All classifiers are sklearn.base.BaseEstimator subclasses and support:

clf.fit(X, y)                              # full batch training
clf.partial_fit(X, y, classes=classes)     # incremental update
clf.predict(X)                             # returns array of class labels
clf.classes_                               # array of known class labels
clf.neuron_list                            # list of neuron dicts

Compatible with scikit-learn pipelines and cross-validation tools that support partial_fit.


Neuron Schema

Learned prototypes are stored in clf.neuron_list as a list of dicts:

{
    'y':             class_label,
    'center':        np.ndarray,     # prototype position
    'cov':           np.ndarray,     # covariance matrix
    'eig_component': np.ndarray,     # PCA eigenvectors
    'width':         np.ndarray,     # semi-axis lengths
    'n':             int,            # sample count
    # SCIL, D4, TRACED only:
    'variance':      np.ndarray,     # eigenvalues
    # TRACED only:
    'displacement':  np.ndarray,     # EMA displacement vector
    'expansion':     np.ndarray,     # EMA per-axis expansion rates
}

Development

# Run tests
pytest tests/ -v

# Run a single test class
pytest tests/test_classifiers.py::TestTRACED -v

# Build for PyPI
pip install build && python -m build

References

  1. VEBF — Jaiyen, S., Lursinsap, C., & Phimoltares, S. (2010). A Very Fast Neural Learning for Classification Using Only New Incoming Datum. IEEE Transactions on Neural Networks, 21(3), 381–392. [paper]
  2. SCIL — Junsawang, P., Phimoltares, S., & Lursinsap, C. (2019). Streaming chunk incremental learning for class-wise data stream classification with fast learning speed and low structural complexity. PLOS ONE, 14(9), e0220624. [paper]
  3. LRHE — Jindadoungrut, K., Phimoltares, S., & Lursinsap, C. (2020). Neural Learning With Recoil Behavior in Hyperellipsoidal Structure. IEEE Access, 8, 114643–114655. [paper]
  4. SHEF — Rungcharassang, P., & Lursinsap, C. (2020). Scalable Hyper-Ellipsoidal Function with Projection Ratio for Local Distributed Streaming Data Classification. IEEE Access, 8, 105460–105474. [paper]
  5. D4 — Wongsriphisant, P., Plaimas, K., & Lursinsap, C. (2026). Markov-based continuous learning with diversion of data distribution direction for streaming data in limited memory. Expert Systems With Applications, 298, 129818. [paper]
  6. TRACED — Wongsriphisant, P., Plaimas, K., & Lursinsap, C. (2026). TRACED: Trend-Adaptive Classification with Ellipsoidal Disambiguation for Resolving Exterior and Coincident Regions in Data Streams. Information Sciences, 743, 123338. [paper]

Citation

If you use this library in your research, please cite the relevant paper(s):

@article{WONGSRIPHISANT2026D4,
    title = {Markov-based continuous learning with diversion of data distribution direction for streaming data in limited memory},
    journal = {Expert Systems with Applications},
    volume = {298},
    pages = {129818},
    year = {2026},
    issn = {0957-4174},
    doi = {https://doi.org/10.1016/j.eswa.2025.129818},
    url = {https://www.sciencedirect.com/science/article/pii/S0957417425034335},
    author = {Peemapat Wongsriphisant and Kitiporn Plaimas and Chidchanok Lursinsap},
}

@article{WONGSRIPHISANT2026TRACED,
    title = {TRACED: Trend-adaptive classification with ellipsoidal disambiguation for resolving exterior and coincident regions in data streams},
    journal = {Information Sciences},
    volume = {743},
    pages = {123338},
    year = {2026},
    issn = {0020-0255},
    doi = {https://doi.org/10.1016/j.ins.2026.123338},
    url = {https://www.sciencedirect.com/science/article/pii/S0020025526002690},
    author = {Peemapat Wongsriphisant and Kitiporn Plaimas and Chidchanok Lursinsap},
}

Notes

  • The original monolithic implementation is preserved at deprecated/spdal.py for reference.
  • Refactoring into the modular src/spdal/ package structure, docstrings, and parameter naming were performed by Claude (Anthropic) and reviewed by the project owner.

Changelog

See CHANGELOG.md. Latest — 0.3.0: TRACED builds its ellipsoid shape matrix with the correct orientation when merging neurons and when tracking their expansion. Neuron counts can shift slightly, and predictions may differ only through the exterior-ambiguity path — see the changelog.

Metadata

Release files for spdal 0.3.0

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for spdal 0.3.0
File Size Uploaded
spdal-0.3.0.tar.gz 48.8 kB Details

Built distribution (wheel)

Table of built distributions (wheels) for spdal 0.3.0
File Interpreter ABI Platform
spdal-0.3.0-py3-none-any.whl Python 3 none any Details

Total release size: 80.2 kB

Release files / spdal-0.3.0.tar.gz

Download URL spdal-0.3.0.tar.gz
Size 48.8 kB
Tags Source
SHA-256 checksum
How to use checksums
d16521b0cad04ecc5b607baee22ab8a110601a5c44379f3a370e848bad907a36
BLAKE2b-256 checksum
How to use checksums
ee727642825f2e0cad3442221119f29f3b9eb9c9ebfc153f191afde76ed4fa94
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.14

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Aug 14, 2026.

Transparency log

Release files / spdal-0.3.0-py3-none-any.whl

Download URL spdal-0.3.0-py3-none-any.whl
Size 31.4 kB
Tags Python 3
SHA-256 checksum
How to use checksums
555ead140f1efa023ee7ba411e9c7d8e4758de180fc863df977a2b2a328bd58f
BLAKE2b-256 checksum
How to use checksums
7b8339ae2453144294ee8df0edbfdca877f6c232b5db9598c4b034732dedb29e
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.14

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Aug 14, 2026.

Transparency log

Release history Release notifications | RSS feed

0.4.1

2 release files

0.4.0

2 release files

This release

0.3.0 This release

2 release files

0.2.0

2 release files

0.1.1

2 release files

0.1.0

2 release files

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page