Skip to content

Commit 59ae27f

Browse files
辰言辰言
authored andcommitted
feat(conversions): add input validation and fix bugs in Roman Numerals
1 parent e3b01ec commit 59ae27f

1 file changed

Lines changed: 37 additions & 1 deletion

File tree

conversions/roman_numerals.py

Lines changed: 37 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,8 +24,25 @@ def roman_to_int(roman: str) -> int:
2424
>>> tests = {"III": 3, "CLIV": 154, "MIX": 1009, "MMD": 2500, "MMMCMXCIX": 3999}
2525
>>> all(roman_to_int(key) == value for key, value in tests.items())
2626
True
27+
>>> roman_to_int("iii")
28+
3
29+
>>> roman_to_int("")
30+
Traceback (most recent call last):
31+
...
32+
ValueError: Input cannot be an empty string
33+
>>> roman_to_int("MIX-abc")
34+
Traceback (most recent call last):
35+
...
36+
ValueError: Invalid Roman numeral character: -
2737
"""
2838
vals = {"I": 1, "V": 5, "X": 10, "L": 50, "C": 100, "D": 500, "M": 1000}
39+
roman = roman.upper()
40+
if not roman:
41+
raise ValueError("Input cannot be an empty string")
42+
for char in roman:
43+
if char not in vals:
44+
raise ValueError(f"Invalid Roman numeral character: {char}")
45+
2946
total = 0
3047
place = 0
3148
while place < len(roman):
@@ -40,12 +57,31 @@ def roman_to_int(roman: str) -> int:
4057

4158
def int_to_roman(number: int) -> str:
4259
"""
43-
Given a integer, convert it to an roman numeral.
60+
Given an integer, convert it to a roman numeral.
4461
https://en.wikipedia.org/wiki/Roman_numerals
4562
>>> tests = {"III": 3, "CLIV": 154, "MIX": 1009, "MMD": 2500, "MMMCMXCIX": 3999}
4663
>>> all(int_to_roman(value) == key for key, value in tests.items())
4764
True
65+
>>> int_to_roman(0)
66+
Traceback (most recent call last):
67+
...
68+
ValueError: Input must be an integer between 1 and 3999
69+
>>> int_to_roman(-5)
70+
Traceback (most recent call last):
71+
...
72+
ValueError: Input must be an integer between 1 and 3999
73+
>>> int_to_roman(4000)
74+
Traceback (most recent call last):
75+
...
76+
ValueError: Input must be an integer between 1 and 3999
77+
>>> int_to_roman(1.5) # type: ignore[arg-type]
78+
Traceback (most recent call last):
79+
...
80+
ValueError: Input must be an integer between 1 and 3999
4881
"""
82+
if not isinstance(number, int) or not (0 < number < 4000):
83+
raise ValueError("Input must be an integer between 1 and 3999")
84+
4985
result = []
5086
for arabic, roman in ROMAN:
5187
(factor, number) = divmod(number, arabic)

0 commit comments

Comments
 (0)