## Posted By

Scooter on 05/19/08

## Who likes this?

3 people have marked this snippet as a favorite

# Roman Numerals

/ Published in: PHP

A library of functions for converting between Arabic and Roman numerals.

`<?php    /*    PHP Roman Numeral Library     Copyright (c) 2008, reusablecode.blogspot.com; some rights reserved.     This work is licensed under the Creative Commons Attribution License. To view    a copy of this license, visit http://creativecommons.org/licenses/by/3.0/ or    send a letter to Creative Commons, 559 Nathan Abbott Way, Stanford, California    94305, USA.    */     // Convert Arabic numerals into Roman numerals.    function roman(\$arabic)    {        \$fractions = Array("", "â�¢", "â�¢â�¢", "â�¢â�¢â�¢", "â�¢â�¢â�¢â�¢", "â�¢â�¢â�¢â�¢â�¢", "S", "Sâ�¢", "Sâ�¢â�¢", "Sâ�¢â�¢â�¢", "Sâ�¢â�¢â�¢â�¢", "Sâ�¢â�¢â�¢â�¢â�¢", "I");        \$ones = Array("", "I", "II", "III", "IV", "V", "VI", "VII", "VIII", "IX");        \$tens = Array("", "X", "XX", "XXX", "XL", "L", "LX", "LXX", "LXXX", "XC");        \$hundreds = Array("", "C", "CC", "CCC", "CD", "D", "DC", "DCC", "DCCC", "CM");        \$thousands = Array("", "M", "MM", "MMM", "MMMM");         if (\$arabic > 4999)        {            // For large numbers (five thousand and above), a bar is placed above a base numeral to indicate multiplication by 1000.            // Since it is not possible to illustrate this in plain ASCII, this function will refuse to convert numbers above 4999.            die("Cannot represent numbers larger than 4999 in plain ASCII.");        }        elseif (\$arabic == 0)        {            // About 725, Bede or one of his colleagues used the letter N, the initial of nullae,            // in a table of epacts, all written in Roman numerals, to indicate zero.            return "N";        }        else        {            // Handle fractions that will round up to 1.            if (round(fmod(\$arabic, 1) * 12) == 12)            {                \$arabic = round(\$arabic);            }             // With special cases out of the way, we can proceed.            // NOTE: modulous operator (%) only supports integers, so fmod() had to be used instead to support floating point.            \$roman = \$thousands[(\$arabic - fmod(\$arabic, 1000)) / 1000];            \$arabic = fmod(\$arabic, 1000);            \$roman .= \$hundreds[(\$arabic - fmod(\$arabic, 100)) / 100];            \$arabic = fmod(\$arabic, 100);            \$roman .= \$tens[(\$arabic - fmod(\$arabic, 10)) / 10];            \$arabic = fmod(\$arabic, 10);            \$roman .= \$ones[(\$arabic - fmod(\$arabic, 1)) / 1];            \$arabic = fmod(\$arabic, 1);             // Handling for fractions.            if (\$arabic > 0)            {                \$roman .= \$fractions[round(\$arabic * 12)];            }             return \$roman;        }    }     // Expand subtractive notation in Roman numerals.    function roman_expand(\$roman)    {        \$roman = str_replace("CM", "DCCCC", \$roman);        \$roman = str_replace("CD", "CCCC", \$roman);        \$roman = str_replace("XC", "LXXXX", \$roman);        \$roman = str_replace("XL", "XXXX", \$roman);        \$roman = str_replace("IX", "VIIII", \$roman);        \$roman = str_replace("IV", "IIII", \$roman);        return \$roman;    }     // Compress Roman numerals using subtractive notation.    function roman_compress(\$roman)    {        \$roman = str_replace("DCCCC", "CM", \$roman);        \$roman = str_replace("CCCC", "CD", \$roman);        \$roman = str_replace("LXXXX", "XC", \$roman);        \$roman = str_replace("XXXX", "XL", \$roman);        \$roman = str_replace("VIIII", "IX", \$roman);        \$roman = str_replace("IIII", "IV", \$roman);        return \$roman;    }     // Convert Roman numerals into Arabic numerals.    function arabic(\$roman)    {        \$result = 0;         // Remove subtractive notation.        \$roman = roman_expand(\$roman);         // Calculate for each numeral.        \$result += substr_count(\$roman, 'M') * 1000;        \$result += substr_count(\$roman, 'D') * 500;        \$result += substr_count(\$roman, 'C') * 100;        \$result += substr_count(\$roman, 'L') * 50;        \$result += substr_count(\$roman, 'X') * 10;        \$result += substr_count(\$roman, 'V') * 5;        \$result += substr_count(\$roman, 'I');        return \$result;    }     // Validate a roman numeral.    function isRoman(\$roman)    {        return preg_match("/[MDCLXVI]/u", \$roman);    }?>`