melon-strings 🍈
Readable and fast string matching for Python.
melon-strings is two libraries in one package:
melon.pure— the explainable half. Dependency-free, heavily commented reference implementations of the entire Charras–Lecroq "Exact String Matching Algorithms" catalog (35 algorithms), plus a classic Aho–Corasick automaton. Written to be read — every module explains the idea and the complexity in plain English.melon.fast— the optimized half. A hand-written C++ trie engine (built with pybind11) powering a keyword extractor/replacer that matches or beatsflashtext, with an automatic pure-Python fallback when the extension isn't compiled.
Copyright 2026 alvations. Licensed under Apache-2.0.
Install
pip install melon-strings # builds the C++ backend if a compiler exists
From a checkout:
pip install -e .
If no C++ compiler is available the install still succeeds and the library
transparently uses the pure-Python engine (melon.fast.is_native_available()
tells you which backend is active).
Keyword extraction & replacement (the flashtext-style API)
from melon import KeywordProcessor # auto-selects the C++ backend
kp = KeywordProcessor()
kp.add_keyword("New York", "NYC") # keyword -> clean name
kp.add_keyword("machine learning")
kp.extract_keywords("machine learning jobs in New York")
# ['machine learning', 'NYC']
kp.replace_keywords("machine learning jobs in New York")
# 'machine learning jobs in NYC'
kp.extract_keywords("the cat sat", span_info=True)
# [('cat', 4, 7)] # exact character spans
What it does that flashtext does — and more
| Capability | flashtext | melon-strings |
|---|---|---|
Trie-based O(n) extraction & replacement |
✅ | ✅ |
add_keyword / remove_keyword / from list / from dict |
✅ | ✅ |
| Case-insensitive matching, clean-name mapping | ✅ | ✅ |
span_info positions |
✅ | ✅ (+extract_keywords_with_span) |
Dict-like API (kp[k]=v, k in kp, del kp[k], len, iter) |
partial | ✅ |
| Configurable word boundaries | ✅ | ✅ |
Raw substring mode (word_boundary=False) |
❌ | ✅ |
Unicode word boundaries (unicode=True) |
❌ | ✅ |
Replacement counts (return_count=True) |
❌ | ✅ |
| C++ backend + identical pure fallback | ❌ | ✅ |
# One-ups
kp.replace_keywords("cat cat", return_count=True) # ('cat cat', 2)
KeywordProcessor(word_boundary=False) # match substrings anywhere
KeywordProcessor(unicode=True) # Unicode-aware boundaries
Pick a backend explicitly if you like:
from melon.pure.keyword import KeywordProcessor as PureKP # always pure Python
from melon.fast import KeywordProcessor as FastKP # C++ (falls back to pure)
The exact-matching algorithm zoo (melon.pure.exact)
Every algorithm exposes the same interface, so they're drop-in interchangeable:
from melon.pure.exact import boyer_moore, ALGORITHMS
boyer_moore.search("abracadabra", "abra") # [0, 7] -> all start indices
list(boyer_moore.finditer("abracadabra", "abra")) # lazy iterator
# Iterate over the whole catalog:
for name, module in ALGORITHMS.items():
assert module.search("banana", "ana") == [1, 3]
All 35 algorithms from the Charras–Lecroq catalog are implemented and validated
against a brute-force oracle on thousands of random cases. See
docs/algorithms.md for the full annotated list.
from melon.pure.multi import AhoCorasick # multi-pattern, all occurrences
ac = AhoCorasick(["he", "she", "his", "hers"])
[(m.start, m.end, m.keyword) for m in ac.finditer("ushers")]
# [(1, 4, 'she'), (2, 4, 'he'), (2, 6, 'hers')]
Command line
melon extract --keywords keywords.txt document.txt # or: python -m melon ...
melon extract --keywords keywords.txt --spans doc.txt # with char offsets
melon replace --keywords map.txt --count doc.txt # key=clean lines
melon search --algorithm boyer_moore --pattern cat doc.txt
melon algorithms # list every algorithm
Development
pip install -e ".[test]"
python scripts/validate.py # brute-force oracle over every algorithm
pytest -q # full test suite
pytest --doctest-modules src/melon # the docstring examples are runnable
python benchmarks/benchmark.py # pure vs C++ vs flashtext vs regex
License
Apache License 2.0 — see LICENSE and NOTICE.
The melon.pure algorithms are educational reimplementations based on Charras &
Lecroq's descriptions; the keyword API is inspired by flashtext / flashtext2.
Metadata
Release files for melon-browser 0.1.0
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | Provenance | Actions |
|---|---|---|---|---|
| melon_browser-0.1.0.tar.gz | 69.6 kB | Without provenance | Details for melon_browser-0.1.0.tar.gz |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Actions Reset |
|---|---|---|---|---|
| melon_browser-0.1.0-cp39-cp39-macosx_10_14_universal2.whl | CPython 3.9 | CPython 3.9 | macOS 10.14+ universal2 (ARM64, x86-64) | Details for melon_browser-0.1.0-cp39-cp39-macosx_10_14_universal2.whl |
Total release size: 349.4 kB
Release files / melon_browser-0.1.0.tar.gz
| Download URL | melon_browser-0.1.0.tar.gz |
|---|---|
| Size | 69.6 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
d8b0895a9567992a4120d86bdceece6ec8d6af94edccba26f0b89226ae12ae0b
|
|
BLAKE2b-256 checksum How to use checksums |
88cabc55dadf68222c5e7c3e1524c893067fcc17491836bee75d3e26f6b743f3
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/6.2.0 CPython/3.9.6
|
Release files / melon_browser-0.1.0-cp39-cp39-macosx_10_14_universal2.whl
| Download URL | melon_browser-0.1.0-cp39-cp39-macosx_10_14_universal2.whl |
|---|---|
| Size | 279.8 kB |
| Tags | CPython 3.9 macOS 10.14+ universal2 (ARM64, x86-64) |
|
SHA-256 checksum How to use checksums |
e9cde55c5f7421a4fe3df68f1ac33e00212e4401668a6206275a09868d81e0d1
|
|
BLAKE2b-256 checksum How to use checksums |
047cfd87017be22b47308939b0d3b07c85d7460dac7dcadd4cd4def1fe1fb61d
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/6.2.0 CPython/3.9.6
|
Security for melon-browser 0.1.0
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.
No provenance found
None of the files in this release were uploaded with provenance metadata.
A note on package security
PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.
To learn more about protecting yourself from malicious actors, visit our package security documentation.