#!/usr/bin/python3 # =================================================================== # Converting Roman Numerals To Decimal # # From: stackoverflow.com/questions/9073150/ # converting-roman-numerals-to-decimal # # I found this code on the web. I really like the recursive # approach to solving the problem. (Note: It was originally # written in javascript.) # # =================================================================== # This code does not recognize the following error situation: # # A letter cannot be repeated more than 3 times, and only powers # of 10 can be repeated. IIII converts to 4 but is not # allowed by the rules for roman numerals. # # Perhaps check for bad input before trying to convert? # re.search("IIII") # re.search("XXXX") # re.search("CCCC") # re.search("LL") # re.search("CC") # re.search("DD") # # =================================================================== # Rules for writing roman numerals # (From: www.cuemath.com/numbers/roman-numerals/) # # a. The letters I,X,C can be repeated three time in succession. # L, V, D cannot be repeated or the number is considered to # be invalid. # b. If a lower value digit is written to the left of a higher # value digit, it is subtracted # c. If a lower value digit is written to the right of a higher # value, it is added # d.Only I,X and C can be used as subtractive numerals # # =================================================================== import re import sys # ------------------------------------------------------------------- # ---- convert roman numerals to decimal (recursive function) # ---- input must be all caps # ------------------------------------------------------------------- def roman_to_integer(nstr): print(f'*** roman_to_integer({nstr})') if nstr == '': return 0 if re.match("^M",nstr): return 1000 + roman_to_integer(nstr[1:]) if re.match("^CM",nstr): return 900 + roman_to_integer(nstr[2:]) if re.match("^D",nstr): return 500 + roman_to_integer(nstr[1:]) if re.match("^CD",nstr): return 400 + roman_to_integer(nstr[2:]) if re.match("^C",nstr): return 100 + roman_to_integer(nstr[1:]) if re.match("^XC",nstr): return 90 + roman_to_integer(nstr[2:]) if re.match("^L",nstr): return 50 + roman_to_integer(nstr[1:]) if re.match("^XL",nstr): return 40 + roman_to_integer(nstr[2:]) if re.match("^X",nstr): return 10 + roman_to_integer(nstr[1:]) if re.match("^IX",nstr): return 9 + roman_to_integer(nstr[2:]) if re.match("^V",nstr): return 5 + roman_to_integer(nstr[1:]) if re.match("^IV",nstr): return 4 + roman_to_integer(nstr[2:]) if re.match("^I",nstr): return 1 + roman_to_integer(nstr[1:]) print('error: something bad happened with ({nstr})') sys.exit() # ------------------------------------------------------------------- # ---- main # ------------------------------------------------------------------- if __name__ == '__main__': import user_interface as ui while(True): ui.clear_screen() print() s = ui.get_user_input('Enter roman number: ') if not s: break n = roman_to_integer(s.upper()) print() if n > 0: print(f'roman number is {n} decimal') else: print(f'bad roman number input ({s})') ui.pause()