Claude Code for decimal: Exact Decimal Arithmetic in Python — Claude Skills 360 Blog
Blog / AI / Claude Code for decimal: Exact Decimal Arithmetic in Python
AI

Claude Code for decimal: Exact Decimal Arithmetic in Python

Published: July 16, 2028
Read time: 5 min read
By: Claude Skills 360

Python’s decimal module provides exact decimal floating-point arithmetic. from decimal import Decimal, getcontext, localcontext, ROUND_HALF_UP, ROUND_HALF_EVEN, ROUND_DOWN, InvalidOperation. Decimal: Decimal("0.10") — ALWAYS from string to avoid float imprecision. Decimal(10) — from int is exact. Decimal(0.1) — from float inherits float’s imprecision. getcontext: getcontext().prec = 28 — set global precision. localcontext: with localcontext() as ctx: ctx.prec = 50 — thread-local override. quantize: Decimal("2.675").quantize(Decimal("0.01"), rounding=ROUND_HALF_UP) → Decimal(“2.68”). to_integral_value: Decimal("2.7").to_integral_value(rounding=ROUND_HALF_UP) → Decimal(“3”). ROUND_HALF_UP: 2.5 → 3.0 (everyday). ROUND_HALF_EVEN: 2.5 → 2.0, 3.5 → 4.0 (banker’s rounding, default). ROUND_DOWN / ROUND_FLOOR / ROUND_CEILING. as_tuple: Decimal("3.14").as_tuple() → DecimalTuple(sign=0, digits=(3,1,4), exponent=-2). compare: Decimal("NaN").is_nan(). InvalidOperation: raised on Decimal(“nan”) math. Decimal.from_float: exact representation. fma: Decimal.fma(d, other, third) — fused multiply-add. sqrt: Decimal("2").sqrt(). Claude Code generates money calculators, tax engines, invoice formatters, and currency converters.

CLAUDE.md for decimal

## decimal Stack
- Stdlib: from decimal import Decimal, getcontext, localcontext, ROUND_HALF_UP, ROUND_HALF_EVEN
- ALWAYS init from string: Decimal("0.10")  — NEVER Decimal(0.10)
- Quantize: amount.quantize(Decimal("0.01"), rounding=ROUND_HALF_UP)
- Precision: with localcontext() as ctx: ctx.prec = 50
- Money: store as Decimal; format with f"{amount:,.2f}"
- Errors: catch decimal.InvalidOperation for bad inputs

decimal Financial Calculation Pipeline

# app/money.py — Decimal, quantize, rounding, tax, invoice, currency
from __future__ import annotations

import decimal
from dataclasses import dataclass, field
from decimal import (
    ROUND_CEILING,
    ROUND_DOWN,
    ROUND_FLOOR,
    ROUND_HALF_DOWN,
    ROUND_HALF_EVEN,
    ROUND_HALF_UP,
    ROUND_UP,
    Decimal,
    InvalidOperation,
    getcontext,
    localcontext,
)
from typing import Any, Iterable


# Global precision — 28 is Decimal default; 34 for IEEE 754-2008 128-bit
getcontext().prec = 28


# ─────────────────────────────────────────────────────────────────────────────
# 1. Decimal construction helpers
# ─────────────────────────────────────────────────────────────────────────────

TWO_PLACES  = Decimal("0.01")
FOUR_PLACES = Decimal("0.0001")
ZERO        = Decimal("0")
ONE         = Decimal("1")
HUNDRED     = Decimal("100")


def d(value: str | int | float | Decimal) -> Decimal:
    """
    Safe Decimal constructor — always normalizes via string.

    Example:
        d("1.005")   # Decimal("1.005")
        d(42)        # Decimal("42")
        d(3.14)      # from string repr, avoids float imprecision
    """
    if isinstance(value, Decimal):
        return value
    if isinstance(value, float):
        # Convert via string to avoid float garbage
        return Decimal(str(value))
    try:
        return Decimal(str(value))
    except InvalidOperation as exc:
        raise ValueError(f"Cannot convert {value!r} to Decimal: {exc}") from exc


def parse_decimal(s: str, default: Decimal | None = None) -> Decimal | None:
    """
    Parse a string to Decimal; return default on error.

    Example:
        parse_decimal("  $1,234.56  ")   # Decimal("1234.56")
        parse_decimal("n/a", default=ZERO)  # Decimal("0")
    """
    cleaned = s.strip().lstrip("$").replace(",", "").replace(" ", "")
    try:
        return Decimal(cleaned)
    except InvalidOperation:
        return default


# ─────────────────────────────────────────────────────────────────────────────
# 2. Rounding helpers
# ─────────────────────────────────────────────────────────────────────────────

def round_money(
    amount: Decimal,
    places: int = 2,
    rounding: str = ROUND_HALF_UP,
) -> Decimal:
    """
    Round to a fixed number of decimal places.

    Example:
        round_money(Decimal("2.675"))              # Decimal("2.68")
        round_money(Decimal("1.005"), rounding=ROUND_HALF_EVEN)  # Decimal("1.00") banker's
    """
    quantizer = Decimal(10) ** -places
    return amount.quantize(quantizer, rounding=rounding)


def round_half_even(amount: Decimal, places: int = 2) -> Decimal:
    """Banker's rounding (round half to even) — reduces statistical bias."""
    return round_money(amount, places, ROUND_HALF_EVEN)


def round_up(amount: Decimal, places: int = 2) -> Decimal:
    """Always round up (ceiling for positives)."""
    return round_money(amount, places, ROUND_CEILING)


def round_down(amount: Decimal, places: int = 2) -> Decimal:
    """Always round down (floor for positives)."""
    return round_money(amount, places, ROUND_FLOOR)


def to_int(amount: Decimal, rounding: str = ROUND_HALF_UP) -> int:
    """Round a Decimal to the nearest integer."""
    return int(amount.to_integral_value(rounding=rounding))


# ─────────────────────────────────────────────────────────────────────────────
# 3. Money arithmetic
# ─────────────────────────────────────────────────────────────────────────────

@dataclass
class Money:
    """
    Immutable money value with 2-decimal precision and a currency code.

    Example:
        price  = Money("19.99", "USD")
        tax    = price.apply_rate(Decimal("0.08"))
        total  = price + tax
        print(total)    # "21.59 USD"
    """
    amount:   Decimal
    currency: str = "USD"

    def __post_init__(self) -> None:
        object.__setattr__(self, "amount", round_money(d(self.amount)))  # type: ignore[arg-type]

    def __add__(self, other: "Money") -> "Money":
        self._check_currency(other)
        return Money(self.amount + other.amount, self.currency)

    def __sub__(self, other: "Money") -> "Money":
        self._check_currency(other)
        return Money(self.amount - other.amount, self.currency)

    def __mul__(self, factor: Decimal | int | str | float) -> "Money":
        return Money(self.amount * d(factor), self.currency)

    def __truediv__(self, divisor: Decimal | int | str | float) -> "Money":
        return Money(self.amount / d(divisor), self.currency)

    def __neg__(self) -> "Money":
        return Money(-self.amount, self.currency)

    def __str__(self) -> str:
        return f"{self.amount:,.2f} {self.currency}"

    def apply_rate(self, rate: Decimal | str, places: int = 2) -> "Money":
        """Multiply by a rate and round."""
        return Money(round_money(self.amount * d(rate), places), self.currency)

    def _check_currency(self, other: "Money") -> None:
        if self.currency != other.currency:
            raise ValueError(f"Currency mismatch: {self.currency} vs {other.currency}")


def split_evenly(total: Decimal, n: int, places: int = 2) -> list[Decimal]:
    """
    Split total into n equal parts, distributing remainder cents evenly.

    Example:
        split_evenly(Decimal("10.00"), 3)  # [Decimal("3.34"), Decimal("3.33"), Decimal("3.33")]
    """
    if n <= 0:
        raise ValueError("n must be positive")
    unit   = Decimal(10) ** -places
    per    = round_down(total / n, places)
    rem    = round_money(total - per * n, places)
    pieces = [per] * n
    steps  = int(rem / unit)
    for i in range(steps):
        pieces[i] += unit
    return pieces


# ─────────────────────────────────────────────────────────────────────────────
# 4. Financial calculations
# ─────────────────────────────────────────────────────────────────────────────

def apply_tax(amount: Decimal, tax_rate_pct: Decimal) -> tuple[Decimal, Decimal]:
    """
    Compute tax and total. Returns (tax_amount, total).

    Example:
        tax, total = apply_tax(Decimal("100.00"), Decimal("8.5"))
        # (Decimal("8.50"), Decimal("108.50"))
    """
    tax   = round_money(amount * tax_rate_pct / HUNDRED)
    total = amount + tax
    return tax, total


def apply_discount(
    amount: Decimal,
    discount_pct: Decimal,
) -> tuple[Decimal, Decimal]:
    """
    Apply a percentage discount. Returns (discount_amount, discounted_price).

    Example:
        disc, price = apply_discount(Decimal("120.00"), Decimal("25"))
        # (Decimal("30.00"), Decimal("90.00"))
    """
    disc  = round_money(amount * discount_pct / HUNDRED)
    after = amount - disc
    return disc, after


def compound_interest(
    principal: Decimal,
    annual_rate_pct: Decimal,
    years: int,
    compounds_per_year: int = 12,
    precision: int = 10,
) -> Decimal:
    """
    Compute compound interest final amount.  A = P(1 + r/n)^(nt).

    Example:
        final = compound_interest(Decimal("1000"), Decimal("5"), years=10)
        # Decimal("1647.0094563...")
    """
    with localcontext() as ctx:
        ctx.prec = precision
        r   = annual_rate_pct / HUNDRED
        n   = Decimal(compounds_per_year)
        nt  = Decimal(years * compounds_per_year)
        result = principal * (ONE + r / n) ** nt
    return round_money(result, 10)


def percentage_change(old: Decimal, new: Decimal) -> Decimal:
    """
    Compute percentage change from old to new.

    Example:
        percentage_change(Decimal("80"), Decimal("100"))  # 25.00
    """
    if old == ZERO:
        raise ZeroDivisionError("old value is zero")
    return round_money((new - old) / abs(old) * HUNDRED)


# ─────────────────────────────────────────────────────────────────────────────
# 5. Invoice builder
# ─────────────────────────────────────────────────────────────────────────────

@dataclass
class LineItem:
    description: str
    quantity:    Decimal
    unit_price:  Decimal

    @property
    def subtotal(self) -> Decimal:
        return round_money(self.quantity * self.unit_price)


@dataclass
class Invoice:
    """
    A simple invoice with line items, discount, and tax.

    Example:
        inv = Invoice(tax_rate_pct=Decimal("8.5"), discount_pct=Decimal("10"))
        inv.add("Widget A", 3, "12.99")
        inv.add("Widget B", 1, "49.00")
        print(inv.summary())
    """
    tax_rate_pct:  Decimal = ZERO
    discount_pct:  Decimal = ZERO
    currency:      str     = "USD"
    items:         list[LineItem] = field(default_factory=list)

    def add(
        self,
        description: str,
        quantity: int | str | Decimal,
        unit_price: str | Decimal,
    ) -> "Invoice":
        self.items.append(LineItem(
            description=description,
            quantity=d(quantity),
            unit_price=d(unit_price),
        ))
        return self

    @property
    def subtotal(self) -> Decimal:
        return sum((item.subtotal for item in self.items), ZERO)

    @property
    def discount_amount(self) -> Decimal:
        return round_money(self.subtotal * self.discount_pct / HUNDRED)

    @property
    def taxable(self) -> Decimal:
        return self.subtotal - self.discount_amount

    @property
    def tax_amount(self) -> Decimal:
        return round_money(self.taxable * self.tax_rate_pct / HUNDRED)

    @property
    def total(self) -> Decimal:
        return self.taxable + self.tax_amount

    def summary(self) -> str:
        lines = ["Invoice"]
        for item in self.items:
            lines.append(
                f"  {item.description:30s}  {item.quantity:>6} × "
                f"{item.unit_price:>10,.2f}  = {item.subtotal:>10,.2f} {self.currency}"
            )
        lines += [
            f"  {'Subtotal':42s}  {self.subtotal:>10,.2f} {self.currency}",
        ]
        if self.discount_pct:
            lines.append(
                f"  {'Discount (' + str(self.discount_pct) + '%)':42s}  "
                f"-{self.discount_amount:>9,.2f} {self.currency}"
            )
        if self.tax_rate_pct:
            lines.append(
                f"  {'Tax (' + str(self.tax_rate_pct) + '%)':42s}  "
                f"+{self.tax_amount:>9,.2f} {self.currency}"
            )
        lines.append(f"  {'TOTAL':42s}  {self.total:>10,.2f} {self.currency}")
        return "\n".join(lines)


# ─────────────────────────────────────────────────────────────────────────────
# Demo
# ─────────────────────────────────────────────────────────────────────────────

if __name__ == "__main__":
    print("=== decimal demo ===")

    print("\n--- why string construction matters ---")
    print(f"  float 0.1 + 0.2 = {0.1 + 0.2}")
    print(f"  Decimal('0.1') + Decimal('0.2') = {Decimal('0.1') + Decimal('0.2')}")

    print("\n--- rounding modes ---")
    amount = Decimal("2.675")
    print(f"  ROUND_HALF_UP:   {round_money(amount, rounding=ROUND_HALF_UP)}")
    print(f"  ROUND_HALF_EVEN: {round_money(amount, rounding=ROUND_HALF_EVEN)}")
    print(f"  ROUND_DOWN:      {round_money(amount, rounding=ROUND_DOWN)}")

    print("\n--- Money ---")
    price = Money("19.99")
    qty   = 3
    sub   = price * qty
    tax   = sub.apply_rate(Decimal("0.085"))
    total = sub + tax
    print(f"  price:    {price}")
    print(f"  subtotal: {sub}")
    print(f"  tax:      {tax}")
    print(f"  total:    {total}")

    print("\n--- split_evenly ---")
    parts = split_evenly(Decimal("10.00"), 3)
    print(f"  $10 / 3: {parts}  sum={sum(parts)}")

    print("\n--- apply_tax ---")
    tax, total = apply_tax(Decimal("100.00"), Decimal("8.5"))
    print(f"  tax={tax}  total={total}")

    print("\n--- apply_discount ---")
    disc, after = apply_discount(Decimal("120.00"), Decimal("25"))
    print(f"  disc={disc}  after={after}")

    print("\n--- compound_interest ---")
    final = compound_interest(Decimal("1000"), Decimal("5"), years=10)
    print(f"  $1000 at 5% for 10 years: {final:.4f}")

    print("\n--- percentage_change ---")
    pct = percentage_change(Decimal("80"), Decimal("100"))
    print(f"  80 → 100: {pct}%")

    print("\n--- Invoice ---")
    inv = (
        Invoice(tax_rate_pct=Decimal("8.5"), discount_pct=Decimal("10"))
        .add("Professional Services", 8, "150.00")
        .add("Software License", 1, "299.00")
        .add("Support (annual)", 1, "199.00")
    )
    print(inv.summary())

    print("\n--- parse_decimal ---")
    for raw in ["  $1,234.56  ", "99.99", "n/a", "1_000"]:
        print(f"  {raw!r:20s}{parse_decimal(raw)}")

    print("\n=== done ===")

For the fractions.Fraction alternative — fractions.Fraction provides exact rational arithmetic using arbitrary-precision integers with no rounding at all: Fraction(1, 3) + Fraction(1, 6) = Fraction(1, 2) exactly; decimal.Decimal uses fixed-precision base-10 floating-point with configurable rounding — use Fraction when exact rational math is required (splitting algorithms, continued fractions, symbolic computation), decimal.Decimal for financial applications where base-10 representation, configurable rounding modes, and two-decimal currency semantics are the requirement. For the money / py-moneyed alternative — third-party money libraries (PyPI money, py-moneyed, moneyed) provide Money(amount, currency) objects with multi-currency arithmetic, locale-aware formatting, and exchange rate hooks; stdlib decimal.Decimal has zero dependencies and gives you the arithmetic primitives — use a money library for multi-currency applications needing exchange rate integration and locale formatting, stdlib Decimal for single-currency financial services, billing engines, and anywhere adding a dependency is costly. The Claude Skills 360 bundle includes decimal skill sets covering d()/parse_decimal() safe constructors, round_money()/round_half_even()/round_up()/round_down()/to_int() rounding helpers, Money dataclass with arithmetic operators and apply_rate(), split_evenly() for even bill-splitting with cent distribution, apply_tax()/apply_discount()/compound_interest()/percentage_change() financial functions, and Invoice/LineItem builder with summary(). Start with the free tier to try financial calculation and decimal pipeline code generation.

Keep Reading

AI

Claude Code for email.contentmanager: Python Email Content Accessors

Read and write EmailMessage body content with Python's email.contentmanager module and Claude Code — email contentmanager ContentManager for the class that maps content types to get and set handler functions allowing EmailMessage to support get_content and set_content with type-specific behaviour, email contentmanager raw_data_manager for the ContentManager instance that handles raw bytes and str payloads without any conversion, email contentmanager content_manager for the standard ContentManager instance used by email.policy.default that intelligently handles text plain text html multipart and binary content types, email contentmanager get_content_text for the handler that returns the decoded text payload of a text-star message part as a str, email contentmanager get_content_binary for the handler that returns the raw decoded bytes payload of a non-text message part, email contentmanager get_data_manager for the get-handler lookup used by EmailMessage get_content to find the right reader function for the content type, email contentmanager set_content text for the handler that creates and sets a text part correctly choosing charset and transfer encoding, email contentmanager set_content bytes for the handler that creates and sets a binary part with base64 encoding and optional filename Content-Disposition, email contentmanager EmailMessage get_content for the method that reads the message body using the registered content manager handlers, email contentmanager EmailMessage set_content for the method that sets the message body and MIME headers in one call, email contentmanager EmailMessage make_alternative make_mixed make_related for the methods that convert a simple message into a multipart container, email contentmanager EmailMessage add_attachment for the method that attaches a file or bytes to a multipart message, and email contentmanager integration with email.message and email.policy and email.mime and io for building high-level email readers attachment extractors text body accessors HTML readers and policy-aware MIME construction pipelines.

5 min read Feb 12, 2029
AI

Claude Code for email.charset: Python Email Charset Encoding

Control header and body encoding for international email with Python's email.charset module and Claude Code — email charset Charset for the class that wraps a character set name with the encoding rules for header encoding and body encoding describing how to encode text for that charset in email messages, email charset Charset header_encoding for the attribute specifying whether headers using this charset should use QP quoted-printable encoding BASE64 encoding or no encoding, email charset Charset body_encoding for the attribute specifying the Content-Transfer-Encoding to use for message bodies in this charset such as QP or BASE64, email charset Charset output_codec for the attribute giving the Python codec name used to encode the string to bytes for the wire format, email charset Charset input_codec for the attribute giving the Python codec name used to decode incoming bytes to str, email charset Charset get_output_charset for returning the output charset name, email charset Charset header_encode for encoding a header string using the charset's header_encoding method, email charset Charset body_encode for encoding body content using the charset's body_encoding, email charset Charset convert for converting a string from the input_codec to the output_codec, email charset add_charset for registering a new charset with custom encoding rules in the global charset registry, email charset add_alias for adding an alias name that maps to an existing registered charset, email charset add_codec for registering a codec name mapping for use by the charset machinery, and email charset integration with email.message and email.mime and email.policy and email.encoders for building international email senders non-ASCII header encoders Content-Transfer-Encoding selectors charset-aware message constructors and MIME encoding pipelines.

5 min read Feb 11, 2029
AI

Claude Code for email.utils: Python Email Address and Header Utilities

Parse and format RFC 2822 email addresses and dates with Python's email.utils module and Claude Code — email utils parseaddr for splitting a display-name plus angle-bracket address string into a realname and email address tuple, email utils formataddr for combining a realname and address string into a properly quoted RFC 2822 address with angle brackets, email utils getaddresses for parsing a list of raw address header strings each potentially containing multiple comma-separated addresses into a list of realname address tuples, email utils parsedate for parsing an RFC 2822 date string into a nine-tuple compatible with time.mktime, email utils parsedate_tz for parsing an RFC 2822 date string into a ten-tuple that includes the UTC offset timezone in seconds, email utils parsedate_to_datetime for parsing an RFC 2822 date string into an aware datetime object with timezone, email utils formatdate for formatting a POSIX timestamp or the current time as an RFC 2822 date string with optional usegmt and localtime flags, email utils format_datetime for formatting a datetime object as an RFC 2822 date string, email utils make_msgid for generating a globally unique Message-ID string with optional idstring and domain components, email utils decode_rfc2231 for decoding an RFC 2231 encoded parameter value into a tuple of charset language and value, email utils encode_rfc2231 for encoding a string as an RFC 2231 encoded parameter value, email utils collapse_rfc2231_value for collapsing a decoded RFC 2231 tuple to a Unicode string, and email utils integration with email.message and email.headerregistry and datetime and time for building address parsers date formatters message-id generators header extractors and RFC-compliant email construction utilities.

5 min read Feb 10, 2029

Put these ideas into practice

Claude Skills 360 gives you production-ready skills for everything in this article — and 2,350+ more. Start free or go all-in.

Back to Blog

Get 360 skills free