Rule-based number formatting using Unicode CLDR data
Project Links
Meta
Author: Michael Hansen
Requires Python: >=3.8.0
Classifiers
Development Status
- 3 - Alpha
Intended Audience
- Developers
Topic
- Text Processing :: Linguistic
License
- OSI Approved :: MIT License
Programming Language
- Python :: 3.8
- Python :: 3.9
- Python :: 3.10
- Python :: 3.11
- Python :: 3.12
- Python :: 3.13
Unicode RBNF
A pure Python implementation of rule based number formatting (RBNF) using the Unicode Common Locale Data Repository (CLDR).
This lets you spell out numbers for a large number of locales:
from unicode_rbnf import RbnfEngine
engine = RbnfEngine.for_language("en")
assert engine.format_number(1234).text == "one thousand two hundred thirty-four"
Different formatting purposes are supported as well, depending on the locale:
from unicode_rbnf import RbnfEngine, FormatPurpose
engine = RbnfEngine.for_language("en")
assert engine.format_number(1999, FormatPurpose.CARDINAL).text == "one thousand nine hundred ninety-nine"
assert engine.format_number(1999, FormatPurpose.YEAR).text == "nineteen ninety-nine"
assert engine.format_number(11, FormatPurpose.ORDINAL).text == "eleventh"
For locales with multiple genders, cases, etc., the different texts are accessible in the result of format_number:
from unicode_rbnf import RbnfEngine
engine = RbnfEngine.for_language("de")
print(engine.format_number(1))
Result:
FormatResult(
text='eins',
text_by_ruleset={
'spellout-numbering': 'eins',
'spellout-cardinal-neuter': 'ein',
'spellout-cardinal-masculine': 'ein',
'spellout-cardinal-feminine': 'eine',
'spellout-cardinal-n': 'einen',
'spellout-cardinal-r': 'einer',
'spellout-cardinal-s': 'eines',
'spellout-cardinal-m': 'einem'
}
)
The text property of the result holds the text of the ruleset with the shortest name (least specific).
Supported locales
See: https://github.com/unicode-org/cldr/tree/release-44/common/rbnf
Engine implementation
Not all features of the RBNF engine are implemented. The following features are available:
- Literal text (
hundred) - Quotient substitution (
<<or←←) - Reminder substitution (
>>or→→) - Optional substitution (
[...]) - Rule substituton (
←%ruleset_name←) - Rule replacement (
=%ruleset_name=) - Special rules:
- Negative numbers (
-x) - Improper fractions (
x.x) - Not a number (
NaN) - Infinity (
Inf)
- Negative numbers (
Some features that will need to be added eventually:
- Proper fraction rules (
0.x) - Preceding reminder substitution (
>>>or→→→) - Number format strings (
==) - Decimal format patterns (
#,##0.00) - Plural replacements (
$(ordinal,one{st}...))
2.4.0
Oct 07, 2025
2.3.0
Feb 18, 2025
2.2.0
Dec 31, 2024
2.1.0
Nov 18, 2024
2.0.0
Oct 24, 2024
1.3.0
Oct 01, 2024
1.2.0
Jul 10, 2024
1.1.0
Feb 06, 2024
1.0.0
Oct 31, 2023