Function: Convert Numbers to Words

August 8, 2010

This little, recursive, script is to convert a number, an integer, to words. It has an upper limit of 999,999,999 but you can expand or reduce it from there.

Put the function in your include file and try it out.

/* 
 *  Function:    number_to_words 
 *  Description:  recursive numerics to words function
 *  Converts a given integer (in range [0..B-1], inclusive) into 
 *  alphabetical format ("one", "two", etc.)
 *  @int
 *  @return string  
 */ 

function number_to_words($number) 
{
    if (($number < 0) || ($number > 999999999)) 
    {
       throw new Exception("Number is out of range");
    }

    $Gn = floor($number / 1000000);  /* Millions (giga) */ 
    $number -= $Gn * 1000000; 
    $kn = floor($number / 1000);     /* Thousands (kilo) */ 
    $number -= $kn * 1000; 
    $Hn = floor($number / 100);      /* Hundreds (hecto) */ 
    $number -= $Hn * 100; 
    $Dn = floor($number / 10);       /* Tens (deca) */ 
    $n = $number % 10;               /* Ones */ 

    $result = ""; 

    if ($Gn) 
    {  $result .= number_to_words($Gn) . " Million";  } 

    if ($kn) 
    {  $result .= (empty($result) ? "" : " ") . 
                   number_to_words($kn) . " Thousand"; } 

    if ($Hn) 
    {  $result .= (empty($result) ? "" : " ") . 
                   number_to_words($Hn) . " Hundred";  } 

    $ones = array("", "One", "Two", "Three", "Four", 
        "Five", "Six", "Seven", "Eight", "Nine", "Ten", 
        "Eleven", "Twelve", "Thirteen", "Fourteen", 
        "Fifteen", "Sixteen", "Seventeen", "Eighteen", 
        "Nineteen"); 
    $tens = array("", "", "Twenty", "Thirty", "Forty", 
        "Fifty", "Sixty", "Seventy", "Eighty", "Ninety"); 

    if ($Dn || $n) 
    { 
       if (!empty($result)) 
       {  $result .= " and ";  
       } 

       if ($Dn < 2) 
       {  $result .= $ones[$Dn * 10 + $n];   
       } 
       else 
       {  $result .= $tens[$Dn]; 
          if ($n) 
          {  $result .= "-" . $ones[$n];  
          } 
       } 
    }

    if (empty($result)) 
    {  $result = "zero"; } 

    return $result; 
} 

For an example, I could use it in my captcha prompt below. Recently, I have had

$Rnum1 = rand(20, 155) ;
$Rnum2 = rand( 1, 5) ; # the ranges are inclusive.
$_SESSION['captcha_correct_answer'] = $Rnum1 - $Rnum2 ;
...
Starting with < ?php echo $Rnum1; ?> give away < ?php echo $Rnum2; ?>
to get < input type="text" name="captcha" maxlength="40" size="4" />
(the answer, to stop automated spam)

What we need to add is these 2 statements right after the "$_SESSION[..." line:

$Rnum1 = number_to_words($Rnum1) ;
$Rnum2 = number_to_words($Rnum2) ;

6 Responses to Function: Convert Numbers to Words

  1. Mujeeb Rehman O on May 5, 2011 at 2:14 am

    thank you for the function


    You are welcome.

  2. Wrayski on June 24, 2011 at 12:57 am

    Hey Greg,
    Awesome function you saved me so much time. Thanks… Wrayski


    glad it helped!

  3. sahswath on August 25, 2011 at 9:04 am

    this code will not work for decimal value

  4. Pablo on October 12, 2011 at 2:08 pm

    Added decimal value (recursive):
    2 decimal values (rounded) . . . modified for dollars and cents

    function number_to_words($number)
    {
        if ($number > 999999999)
        {
           throw new Exception("Number is out of range");
        }
    
        $Gn = floor($number / 1000000);  /* Millions (giga) */
        $number -= $Gn * 1000000;
        $kn = floor($number / 1000);     /* Thousands (kilo) */
        $number -= $kn * 1000;
        $Hn = floor($number / 100);      /* Hundreds (hecto) */
        $number -= $Hn * 100;
        $Dn = floor($number / 10);       /* Tens (deca) */
        $n = $number % 10;               /* Ones */ 
    	$cn = round(($number-floor($number))*100); /* Cents */
        $result = ""; 
    
        if ($Gn)
        {  $result .= number_to_words($Gn) . " Million";  } 
    
        if ($kn)
        {  $result .= (empty($result) ? "" : " ") . number_to_words($kn) . " Thousand"; } 
    
        if ($Hn)
        {  $result .= (empty($result) ? "" : " ") . number_to_words($Hn) . " Hundred";  } 
    
        $ones = array("", "One", "Two", "Three", "Four", "Five", "Six",
            "Seven", "Eight", "Nine", "Ten", "Eleven", "Twelve", "Thirteen",
            "Fourteen", "Fifteen", "Sixteen", "Seventeen", "Eightteen",
            "Nineteen");
        $tens = array("", "", "Twenty", "Thirty", "Fourty", "Fifty", "Sixty",
            "Seventy", "Eigthy", "Ninety"); 
    
        if ($Dn || $n)
        {
           if (!empty($result))
           {  $result .= " and ";
           } 
    
           if ($Dn < 2)
           {  $result .= $ones[$Dn * 10 + $n];
           }
           else
           {  $result .= $tens[$Dn];
              if ($n)
              {  $result .= "-" . $ones[$n];
              }
           }
        }
        
        if ($cn)
        {
           if (!empty($result))
           {  $result .= ' and ';
           }
           $title = $cn==1 ? 'cent ': 'cents';
           $result .= strtolower(number_to_words($cn)).' '.$title;
        }
    
        if (empty($result))
        {  $result = "zero"; } 
    
        return $result;
    } 
     

    Test:
    80.5: Eigthy and fifty cents
    400342.22: Four Hundred Thousand Three Hundred and Fourty-Two and twenty-two cents
    80.1: Eigthy and ten cents
    80.01: Eigthy and one cent
    80: Eigthy
    8050: Eight Thousand and Fifty
    0: zero
    0.53: fifty-three cents


    Nice job!
    Now, just fix a few spelling errors, and a person can add “dollars” or whatever, and replace “cents” or whatever their currency is, and they are done.
    PS since this is only for currencies, I would rename the function to denote that.

  5. Ep on November 23, 2012 at 1:23 am

    Now if we could just run spellcheck on this.


    Yes, Ha!

  6. Freethinkersaif on March 23, 2016 at 4:09 pm

    Awesome post. Great work. Thanks a lot.

We try to post all comments within 1 business day