DEV Community

Cover image for Building a Client-Side Number to Words Converter: A Lesson in Structural Parsing
Vo Viet Hoang
Vo Viet Hoang

Posted on

Building a Client-Side Number to Words Converter: A Lesson in Structural Parsing

Hey DEV community! 👋

In software engineering, text processing, and administrative workflows, we often need to transform raw numerical data into grammatically correct English words. This task is common when auto-generating invoices, creating formalized transactional records, or formatting ledger summaries.

While converting small numbers is straightforward, parsing extremely large values and handling decimals requires a clean, recursive segmentation approach. Moreover, doing this on the client side ensures that sensitive logistical and transactional figures never leave the user's browser.

In this post, we will walk through the algorithmic logic of scale division and look at a clean, vanilla JavaScript implementation to handle this transformation strictly locally.


The Algorithmic Structure of Numerical Scales

Converting numbers into words requires dividing the standard base-10 numerical sequence into manageable chunks. In English, numbering scales follow a periodic three-digit pattern (Ones, Tens, Hundreds), which is repeated across scale suffixes (Thousand, Million, Billion, etc.).

Our algorithm implements a sliding scale division. For any given input, we process the value in modulo-1000 chunks:

Chunk=Value(mod1000)\text{Chunk} = \text{Value} \pmod{1000}

We then update the remaining value by moving to the next scale index:

Next Value=⌊Value1000⌋\text{Next Value} = \lfloor \frac{\text{Value}}{1000} \rfloor

This approach lets us isolate each three-digit segment, convert it to words using simple array mappings, and append the correct scale designation (like thousand or million) before moving to the next block.


Client-Side JavaScript Implementation

Below is the structured, modular JavaScript function that handles the conversion. It is designed to process the integer portion through modular division, while supporting optional currency formatting or decimal point representations:

/**
 * Converts a positive integer into written English words.
 * @param {number} num - The positive integer to convert
 * @returns {string} The written representation
 */
function toEnglishWords(num) {
    if (num === 0) return 'zero';

    const ones = ['', 'one', 'two', 'three', 'four', 'five', 'six', 'seven', 'eight', 'nine', 'ten', 'eleven', 'twelve', 'thirteen', 'fourteen', 'fifteen', 'sixteen', 'seventeen', 'eighteen', 'nineteen'];
    const tens = ['', '', 'twenty', 'thirty', 'forty', 'fifty', 'sixty', 'seventy', 'eighty', 'ninety'];
    const scales = ['', 'thousand', 'million', 'billion', 'trillion'];

    let words = [];
    let scaleIdx = 0;

    while (num > 0) {
        let chunk = num % 1000;
        if (chunk > 0) {
            let chunkWords = [];
            let hundreds = Math.floor(chunk / 100);
            let remainder = chunk % 100;

            if (hundreds > 0) {
                chunkWords.push(ones[hundreds] + ' hundred');
            }

            if (remainder > 0) {
                if (remainder < 20) {
                    chunkWords.push(ones[remainder]);
                } else {
                    let tenDigit = Math.floor(remainder / 10);
                    let oneDigit = remainder % 10;
                    chunkWords.push(tens[tenDigit] + (oneDigit > 0 ? '-' + ones[oneDigit] : ''));
                }
            }

            let chunkStr = chunkWords.join(' ');
            if (scales[scaleIdx]) {
                chunkStr += ' ' + scales[scaleIdx];
            }
            words.unshift(chunkStr);
        }
        num = Math.floor(num / 1000);
        scaleIdx++;
    }

    return words.join(' ');
}
Enter fullscreen mode Exit fullscreen mode

Key Technical Aspects:

  • Sub-20 Array Mapping: Numbers from 1 to 19 have unique English designations, so they are mapped directly to a flat array.
  • Hyphenation Rule: Numbers from 21 to 99 are joined with a hyphen (e.g., twenty-five) to follow standard English writing conventions.
  • Memory Optimization: By managing parsing entirely within local variables, the utility handles large scales smoothly without page latency.

Ensuring User Privacy and Safety

Many online web calculators send your form inputs back to their servers. When dealing with raw invoicing figures or database records, this is an unnecessary security risk.

By executing the string formatting entirely in local browser memory:

  • No Database Logging: Your values are processed temporarily and discarded when the fields are reset.
  • Lightweight Performance: Standard JS array operations require minimal resources, keeping the page loading footprint tiny.

Designing a Clean Web Utility

The converter layout organizes user input and output fields using simple, responsive elements:

  1. Interactive Inputs: A text area that automatically ignores non-numeric characters to ensure clean data streams.
  2. Dynamic Format Selector: An optional configuration to format the output with standard currency subunits (like US Dollars and Cents).
  3. Instant Output Card: Displays the parsed string in real time with proper capitalization.

If you are looking for a reliable, browser-based tool to convert numerical records into formal text strings, feel free to try the live utility:

👉 Live Link: Online Number to Words Converter


Let's Connect!

What is your preferred approach for formatting technical strings and logistical logs in your development workflows? Do you rely on local command-line tools or keep a directory of secure browser utilities?

Let's discuss in the comments below! Happy coding! 🚀

Top comments (1)

Collapse
 
hoangvibecode profile image
Vo Viet Hoang

Let's discuss in the comments below! Happy coding!