From e510a036a2e6673f3ff4bafbf9f717c7ea20b988 Mon Sep 17 00:00:00 2001 From: Faizzyhon <68625839+faizzyhon@users.noreply.github.com> Date: Thu, 7 May 2026 02:21:50 +0300 Subject: [PATCH 1/5] fix: int_to_roman silently returns wrong values for out-of-range input Added input validation for int_to_roman function. --- conversions/roman_numerals.py | 27 ++++++++++++++++++++++++++- 1 file changed, 26 insertions(+), 1 deletion(-) diff --git a/conversions/roman_numerals.py b/conversions/roman_numerals.py index 75af2ac72882..2f3af8ed36fb 100644 --- a/conversions/roman_numerals.py +++ b/conversions/roman_numerals.py @@ -40,12 +40,37 @@ def roman_to_int(roman: str) -> int: def int_to_roman(number: int) -> str: """ - Given a integer, convert it to an roman numeral. + Given an integer, convert it to a Roman numeral. + Input must be an integer in the range 1 to 3999. https://en.wikipedia.org/wiki/Roman_numerals >>> tests = {"III": 3, "CLIV": 154, "MIX": 1009, "MMD": 2500, "MMMCMXCIX": 3999} >>> all(int_to_roman(value) == key for key, value in tests.items()) True + >>> int_to_roman(0) + Traceback (most recent call last): + ... + ValueError: int_to_roman only accepts integers in the range 1 to 3999, got 0 + >>> int_to_roman(-1) + Traceback (most recent call last): + ... + ValueError: int_to_roman only accepts integers in the range 1 to 3999, got -1 + >>> int_to_roman(4000) + Traceback (most recent call last): + ... + ValueError: int_to_roman only accepts integers in the range 1 to 3999, got 4000 + >>> int_to_roman(True) + Traceback (most recent call last): + ... + TypeError: int_to_roman only accepts integers, got bool """ + if not isinstance(number, int) or isinstance(number, bool): + raise TypeError( + f"int_to_roman only accepts integers, got {type(number).__name__}" + ) + if not 1 <= number <= 3999: + raise ValueError( + f"int_to_roman only accepts integers in the range 1 to 3999, got {number}" + ) result = [] for arabic, roman in ROMAN: (factor, number) = divmod(number, arabic) From 96d953ef3d2c1ca3ab1aaa437a5e14f060d11594 Mon Sep 17 00:00:00 2001 From: Faizzyhon <68625839+faizzyhon@users.noreply.github.com> Date: Wed, 6 May 2026 16:34:50 -0700 Subject: [PATCH 2/5] fix: EM102 assign f-strings to msg before raising exceptions --- conversions/roman_numerals.py | 10 ++++------ 1 file changed, 4 insertions(+), 6 deletions(-) diff --git a/conversions/roman_numerals.py b/conversions/roman_numerals.py index 2f3af8ed36fb..40ee2203d0f5 100644 --- a/conversions/roman_numerals.py +++ b/conversions/roman_numerals.py @@ -64,13 +64,11 @@ def int_to_roman(number: int) -> str: TypeError: int_to_roman only accepts integers, got bool """ if not isinstance(number, int) or isinstance(number, bool): - raise TypeError( - f"int_to_roman only accepts integers, got {type(number).__name__}" - ) + msg = f"int_to_roman only accepts integers, got {type(number).__name__}" + raise TypeError(msg) if not 1 <= number <= 3999: - raise ValueError( - f"int_to_roman only accepts integers in the range 1 to 3999, got {number}" - ) + msg = f"int_to_roman only accepts integers in the range 1 to 3999, got {number}" + raise ValueError(msg) result = [] for arabic, roman in ROMAN: (factor, number) = divmod(number, arabic) From d953d37b9b8dccc8796fa5d0e81acac7159c7046 Mon Sep 17 00:00:00 2001 From: Christian Clauss Date: Wed, 16 Sep 2026 20:04:20 +0200 Subject: [PATCH 3/5] Update conversions/roman_numerals.py --- conversions/roman_numerals.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/conversions/roman_numerals.py b/conversions/roman_numerals.py index 40ee2203d0f5..e2f49c4e3586 100644 --- a/conversions/roman_numerals.py +++ b/conversions/roman_numerals.py @@ -63,7 +63,7 @@ def int_to_roman(number: int) -> str: ... TypeError: int_to_roman only accepts integers, got bool """ - if not isinstance(number, int) or isinstance(number, bool): + if not isinstance(number, (bool, int)): msg = f"int_to_roman only accepts integers, got {type(number).__name__}" raise TypeError(msg) if not 1 <= number <= 3999: From 273af2cd31b973e2498d571f2cb961c87da62d3f Mon Sep 17 00:00:00 2001 From: Christian Clauss Date: Wed, 16 Sep 2026 20:08:44 +0200 Subject: [PATCH 4/5] Bool don't work --- conversions/roman_numerals.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/conversions/roman_numerals.py b/conversions/roman_numerals.py index e2f49c4e3586..032cd9389197 100644 --- a/conversions/roman_numerals.py +++ b/conversions/roman_numerals.py @@ -63,7 +63,7 @@ def int_to_roman(number: int) -> str: ... TypeError: int_to_roman only accepts integers, got bool """ - if not isinstance(number, (bool, int)): + if not isinstance(number, int): msg = f"int_to_roman only accepts integers, got {type(number).__name__}" raise TypeError(msg) if not 1 <= number <= 3999: From 83346fe8655609daa1f615b012b23f19ece4d652 Mon Sep 17 00:00:00 2001 From: Christian Clauss Date: Wed, 16 Sep 2026 21:18:28 +0200 Subject: [PATCH 5/5] Apply suggestion from @cclauss --- conversions/roman_numerals.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/conversions/roman_numerals.py b/conversions/roman_numerals.py index 032cd9389197..7764ee0d8de5 100644 --- a/conversions/roman_numerals.py +++ b/conversions/roman_numerals.py @@ -63,7 +63,7 @@ def int_to_roman(number: int) -> str: ... TypeError: int_to_roman only accepts integers, got bool """ - if not isinstance(number, int): + if isinstance(number, bool) or not isinstance(number, int): msg = f"int_to_roman only accepts integers, got {type(number).__name__}" raise TypeError(msg) if not 1 <= number <= 3999: