Snippets/java/Number to Words Converter
intermediatejava

Number to Words Converter

Convert numbers to words following Indian numbering system (Crores, Lakhs, etc.)

Published August 22, 2024
Updated August 22, 2024
Utility
utilityconverterindian-numberingbigdecimal

Number to Words Converter

Converts numbers into words following the Indian numbering system (Crores, Lakhs, Thousands).

Code

import java.math.BigDecimal;
import java.math.RoundingMode;
 
/**
 * A utility class for converting numbers into words, supporting the Indian numbering system.
 */
public class NumberToWordsConverter {
 
    // Arrays to store word representations of numbers
    private static final String[] units = {
        "", "One", "Two", "Three", "Four", "Five", "Six",
        "Seven", "Eight", "Nine", "Ten", "Eleven", "Twelve",
        "Thirteen", "Fourteen", "Fifteen", "Sixteen",
        "Seventeen", "Eighteen", "Nineteen"
    };
 
    private static final String[] tens = {
        "",        // 0
        "",        // 1
        "Twenty",  // 2
        "Thirty",  // 3
        "Forty",   // 4
        "Fifty",   // 5
        "Sixty",   // 6
        "Seventy", // 7
        "Eighty",  // 8
        "Ninety"   // 9
    };
 
    /**
     * Converts a given amount into words.
     *
     * @param amount The amount to convert (can be Integer, Float, Double, etc.)
     * @return The amount in words
     * @throws IllegalArgumentException if the amount is negative or exceeds 100 crores
     */
    public static String convertNumberToWords(Number amount) {
        // Convert the Number to BigDecimal for precise decimal handling
        BigDecimal bdAmount = new BigDecimal(amount.toString()).setScale(2, RoundingMode.HALF_UP);
 
        // Check if the amount is negative or exceeds 100 crores
        if (bdAmount.compareTo(BigDecimal.ZERO) < 0) {
            throw new IllegalArgumentException("Amount must be positive or zero.");
        }
        BigDecimal maxAmount = new BigDecimal("1000000000"); // 100 crores in rupees
        if (bdAmount.compareTo(maxAmount) >= 0) {
            throw new IllegalArgumentException("Amount must be less than 100 crores.");
        }
 
        // Separate integer and fractional parts
        BigDecimal integerPart = bdAmount.setScale(0, RoundingMode.DOWN);
        BigDecimal fractionalPart = bdAmount.subtract(integerPart).multiply(new BigDecimal(100)).setScale(0, RoundingMode.HALF_UP);
 
        StringBuilder result = new StringBuilder();
 
        // Convert integer part to words
        if (integerPart.compareTo(BigDecimal.ZERO) > 0) {
            result.append(convertIntegerToWords(integerPart.toBigInteger().longValue()));
        } else {
            result.append("Zero");
        }
 
        // Convert fractional part to words, if any
        if (fractionalPart.compareTo(BigDecimal.ZERO) > 0) {
            result.append(" Point");
            char[] fractionDigits = fractionalPart.toPlainString().toCharArray();
            for (char digit : fractionDigits) {
                result.append(" ").append(units[Character.getNumericValue(digit)]);
            }
        }
 
        return result.toString().trim();
    }
 
    /**
     * Helper method to convert integer part into words following the Indian numbering system.
     *
     * @param number The integer number to convert
     * @return The number in words
     */
    private static String convertIntegerToWords(long number) {
        if (number == 0) {
            return "";
        }
 
        StringBuilder word = new StringBuilder();
 
        // Crores place
        if ((number / 10000000) > 0) {
            word.append(convertIntegerToWords(number / 10000000)).append(" Crore ");
            number %= 10000000;
        }
 
        // Lakhs place
        if ((number / 100000) > 0) {
            word.append(convertIntegerToWords(number / 100000)).append(" Lakh ");
            number %= 100000;
        }
 
        // Thousands place
        if ((number / 1000) > 0) {
            word.append(convertIntegerToWords(number / 1000)).append(" Thousand ");
            number %= 1000;
        }
 
        // Hundreds place
        if ((number / 100) > 0) {
            word.append(convertIntegerToWords(number / 100)).append(" Hundred ");
            number %= 100;
        }
 
        // Tens and Units place
        if (number > 0) {
            if (word.length() > 0) {
                word.append("and ");
            }
            if (number < 20) {
                word.append(units[(int) number]).append(" ");
            } else {
                word.append(tens[(int) (number / 10)]).append(" ").append(units[(int) (number % 10)]).append(" ");
            }
        }
 
        return word.toString().trim();
    }
}

Usage

public class Main {
    public static void main(String[] args) {
        // Basic numbers
        System.out.println(NumberToWordsConverter.convertNumberToWords(123));
        // Output: One Hundred and Twenty Three
 
        // Large numbers (Indian system)
        System.out.println(NumberToWordsConverter.convertNumberToWords(12345678));
        // Output: One Crore Twenty Three Lakh Forty Five Thousand Six Hundred and Seventy Eight
 
        // Decimal numbers
        System.out.println(NumberToWordsConverter.convertNumberToWords(123.45));
        // Output: One Hundred and Twenty Three Point Four Five
 
        // Zero
        System.out.println(NumberToWordsConverter.convertNumberToWords(0));
        // Output: Zero
    }
}