Skip to content

Instantly share code, notes, and snippets.

@dermesser
Created July 6, 2014 18:36
Show Gist options
  • Save dermesser/1baefc30d0f20f409569 to your computer and use it in GitHub Desktop.
Save dermesser/1baefc30d0f20f409569 to your computer and use it in GitHub Desktop.
A simple Roman2Decimal2Roman converter. Bugs: Dec2Rom converter uses four consecutive I (like in VIIII); romanToDecimal /may/ be simplified.
import Data.Char (toLower)
rdToDec :: Char -> Int
rdToDec 'i' = 1
rdToDec 'v' = 5
rdToDec 'x' = 10
rdToDec 'l' = 50
rdToDec 'c' = 100
rdToDec 'd' = 500
rdToDec 'm' = 1000
-- Call this function to convert a roman number to a decimal one
romanToDecimal :: String -> Int
romanToDecimal (x':y':z':a') = let (x,y,z,a) = (toLower x',toLower y',toLower z',map toLower a') in
if rdToDec x >= rdToDec y && rdToDec y >= rdToDec z
then (rdToDec x + rdToDec y + rdToDec z) + romanToDecimal a
else if rdToDec x < rdToDec y
then (rdToDec y - rdToDec x) + romanToDecimal (z:a)
else rdToDec x + (rdToDec z - rdToDec y) + romanToDecimal a
romanToDecimal (x':y':z') = let (x,y,z) = (toLower x', toLower y', map toLower z') in
if rdToDec x >= rdToDec y
then (rdToDec x + rdToDec y) + romanToDecimal z
else (rdToDec y - rdToDec x) + romanToDecimal z
romanToDecimal [x] = rdToDec . toLower $ x
romanToDecimal [] = 0
romVals :: [Int]
romVals = [1000,500,100,50,10,5,1]
romDigs :: [Char]
romDigs = ['M','D','C','L','X','V','I']
-- Call this function to convert an Integer to a roman numeral.
decToRom :: Int -> String
decToRom i = f (zip romVals romDigs) i ""
where f ((dv,d):xs) v s = f xs (v `mod` dv) (s ++ (replicate (v `div` dv) d))
f [] v s = s
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment