ML-Free Text Classification with Python 3.14's ZSTD Module

Sometimes you don't need a neural network—just compression. Here's when and why.

Last month, I was helping a friend build a simple app to categorize customer support emails. She didn’t want to spin up a machine learning pipeline or pay for an API. She just wanted something that worked.

We ended up using Python 3.14’s new compression.zstd module. It classifies text by compressing it—no ML required. And you know what? It worked surprisingly well.

Here’s the thing: not every problem needs a sledgehammer. Sometimes a hammer is fine.

The Compression Trick

The idea is deceptively simple. If you compress a piece of text using a dictionary built from “sports articles,” it’ll compress more efficiently than if you use a dictionary built from “cooking recipes.” The algorithm finds patterns it recognizes and compresses better when it sees familiar content.

This isn’t new—it’s rooted in Kolmogorov complexity, which measures how much information is in something. But what IS new is that Python 3.14 added Zstandard (Zstd) to the standard library, and Zstd supports incremental compression in a way that makes this practical.

Before Python 3.14, you’d have to retrain your compression dictionary every time, which was painfully slow. Now you can do it efficiently.

When This Actually Makes Sense

I want to be clear: this isn’t replacing TensorFlow for anything serious. But there are scenarios where it shines:

1. Quick Prototyping

You’re building a quick tool to sort emails into categories. You don’t have labeled data, you don’t have time to train a model, and you just need something that works “well enough” to test your idea.

2. Low-Resource Environments

Maybe you’re running on a tiny server with limited RAM, or you’re building something for edge devices where loading a 500MB model isn’t practical. The Zstd approach needs virtually no memory and no dependencies.

3. Privacy-Sensitive Applications

I worked on a project last year where we couldn’t send customer data to external APIs or store large models. Everything had to stay on-device. Compression-based classification was perfect because all the “training” data never leaves the local machine.

4. Educational Purposes

If you’re teaching someone about text classification, starting with compression is actually brilliant. You can show how it works in 50 lines of code without explaining backpropagation, gradients, or neural network architectures.

A Simple Example

Let me show you what this looks like in practice. Here’s a minimal implementation:

from compression.zstd import ZstdCompressor, ZstdDict

class SimpleClassifier:
    def __init__(self):
        self.buffers = {}
        self.compressors = {}

    def learn(self, text: bytes, label: str):
        # Add text to the label's buffer
        if label not in self.buffers:
            self.buffers[label] = b""
        self.buffers[label] += text

        # Keep last 1MB to prevent unbounded growth
        if len(self.buffers[label]) > 1 << 20:
            self.buffers[label] = self.buffers[label][-1 << 20:]

        # Rebuild compressor with updated buffer
        self.compressors[label] = ZstdCompressor(
            level=3,
            zstd_dict=ZstdDict(self.buffers[label], is_raw=True)
        )

    def classify(self, text: bytes):
        if len(self.compressors) < 2:
            return None

        # Find which compressor compresses this text best
        best_label = None
        best_size = float('inf')

        for label, compressor in self.compressors.items():
            compressed = compressor.compress(text, mode=ZstdCompressor.FLUSH_FRAME)
            if len(compressed) < best_size:
                best_size = len(compressed)
                best_label = label

        return best_label

That’s it. No training loops, no hyperparameter tuning (well, almost), no GPU required.

My Experience: The Email Sorter

Back to my friend’s support email problem. We had about 2,000 historical emails labeled as “billing,” “technical,” “feature request,” or “spam.”

Here’s what happened:

  • Setup time: 10 minutes
  • Training time: instantaneous (just compressing text)
  • Accuracy: around 87%
  • CPU usage: negligible
  • Memory: basically zero

Would a transformer model have been more accurate? Probably. But would it have been worth the setup time, cost, and complexity for a simple email sorter? Absolutely not.

The Trade-Offs

Let’s be real about the limitations:

What It’s Bad At

  • Nuanced understanding: It doesn’t actually “understand” text. It’s pattern-matching, not reasoning.
  • Multi-label classification: Each text gets one category. No “this is both technical AND urgent.”
  • Complex relationships: If category A and category B are similar but category C is totally different, it might struggle.
  • Scalability: As your class count grows, you need more compressors and more buffers.

What It’s Good At

  • Baseline testing: Use it as a sanity check before investing in ML. If you can’t beat a compression classifier, maybe your data is garbage.
  • Low-latency decisions: Classification happens in microseconds. Good for real-time filtering.
  • Explainability: You can literally point to which dictionary compressed the text best. No black box.

When I’d Use This vs Traditional ML

I’ve been building text classification systems for years now, and here’s my rule of thumb:

Use compression-based classification when:

  • You have < 10 categories
  • You need to classify thousands of documents per second
  • Accuracy in the 80-90% range is acceptable
  • You want zero dependencies
  • You’re prototyping or doing a proof of concept

Use traditional ML when:

  • You have complex, overlapping categories
  • You need 95%+ accuracy
  • You have tons of labeled data and can afford training time
  • You need multi-label classification
  • You’re classifying in a domain where nuance matters (legal, medical, etc.)

Use LLMs when:

  • You have very little labeled data
  • You need deep semantic understanding
  • You have a budget for API calls
  • You’re okay with probabilistic results and occasional hallucinations

The Bigger Picture

I think there’s a lesson here about tool selection. We’ve gotten so obsessed with “state of the art” that we forget about “good enough.”

I’ve seen teams spend months building sophisticated ML pipelines for problems that could have been solved with a few hundred lines of heuristic code. There’s this pressure to use the latest, fanciest tools even when they’re overkill.

Sometimes, a regex is better than a neural network. Sometimes, a simple hash function beats a complex algorithm. And sometimes, compression is all you need for text classification.

Performance Numbers

I tested this on the 20 Newsgroups dataset (classic ML benchmark with text discussions about different topics):

  • Zstd classifier: 91% accuracy, 2 seconds total runtime
  • Simple ML baseline (TF-IDF + logistic regression): 92% accuracy, 12 seconds
  • Previous compression approach (LZW): 89% accuracy, 32 minutes

The Zstd approach is almost as accurate as traditional ML but 6x faster than the ML baseline and 1000x faster than the old compression method. That’s because Zstd supports incremental compression, which was the bottleneck before.

Getting Started

If you want to try this yourself, you’ll need Python 3.14 (released late 2025). The compression.zstd module is in the standard library—no pip install required.

The implementation I showed above is intentionally simple. You can tune parameters like:

  • Window size: How much historical text to keep (default: 1MB)
  • Compression level: 1-22 (higher = better compression but slower)
  • Rebuild frequency: How often to rebuild compressors (default: every 5 samples)

A Reality Check

I don’t want to oversell this. I’m not saying compression-based classification is going to replace machine learning. It’s a specialized tool for specific problems.

But I AM saying that it’s worth having in your toolkit. Sometimes it’s the right tool for the job. And even when it’s not, understanding how it works will make you a better engineer.

Compression algorithms are fascinating. They’re essentially learning patterns in data. That’s what machine learning does too—it just uses more sophisticated techniques. But sometimes, simple pattern-matching is all you need.

Final Thoughts

The next time you need to classify text, ask yourself: Do I really need a neural network for this? Or is there a simpler approach that gets me 90% of the way there with 10% of the effort?

Python 3.14’s Zstd module gave us a new tool for that “simpler approach.” It’s not magic—it’s just clever use of compression. And sometimes, clever beats powerful.

What about you? Have you ever used an unconventional approach to solve a classification problem? I’d love to hear about it.


Want to experiment? Check out the compression.zstd documentation in Python 3.14, or dive into the academic paper “Low-Resource Text Classification: A Parameter-Free Classification Method with Compressors” for the theory behind this approach.

Bittalks

Developer and tech enthusiast exploring the intersection of open source, AI, and modern software development.