Skip to content

Commit

Permalink
fix issue #35 + boolean checks for log and is_fidelity
Browse files Browse the repository at this point in the history
  • Loading branch information
danrgll committed Feb 4, 2024
1 parent aa9af08 commit 300b5a3
Show file tree
Hide file tree
Showing 7 changed files with 91 additions and 17 deletions.
26 changes: 20 additions & 6 deletions neps/search_spaces/hyperparameters/categorical.py
Original file line number Diff line number Diff line change
Expand Up @@ -39,19 +39,33 @@ def __init__(
)
self.value: None | float | int | str = None

# Check if 'default' is in 'choices'
if default is not None and default not in self.choices:
raise ValueError(
f"Default value {default} is not in the provided choices {self.choices}"
)

# Check if 'is_fidelity' is a boolean
if not isinstance(is_fidelity, bool):
raise TypeError(
f"Expected 'is_fidelity' to be a boolean, but got type: "
f"{type(is_fidelity).__name__}"
)

@property
def id(self):
return self.value

def __eq__(self, other):
if not isinstance(other, self.__class__):
return False
return (self.choices == other.choices
and self.value == other.value
and self.is_fidelity == other.is_fidelity
and self.default == other.default
and self.default_confidence_score == other.default_confidence_score
)
return (
self.choices == other.choices
and self.value == other.value
and self.is_fidelity == other.is_fidelity
and self.default == other.default
and self.default_confidence_score == other.default_confidence_score
)

def __repr__(self):
return f"<Categorical, choices: {self.choices}, value: {self.value}>"
Expand Down
18 changes: 8 additions & 10 deletions neps/search_spaces/hyperparameters/float.py
Original file line number Diff line number Diff line change
Expand Up @@ -49,17 +49,15 @@ def __init__(
f" upper={self.upper}"
)

if not isinstance(log, bool):
raise TypeError(
f"Expected 'log' to be a boolean, but got type: {type(log).__name__}"
)

if not isinstance(log, bool):
raise TypeError(
"Expected 'self.log' to be a boolean, but got type: {}".format(
type(log).__name__
# Validate 'log' and 'is_fidelity' types to prevent configuration errors
# from the YAML input
for param, value in {"log": log, "is_fidelity": is_fidelity}.items():
if not isinstance(value, bool):
raise TypeError(
f"Expected '{param}' to be a boolean, but got type: "
f"{type(value).__name__}"
)
)

self.log = log

if self.log:
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
search_space:
cat1:
choices: ["a", "b", "c"]
default: "d"
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
search_space:
cat1:
choices: ["a", "b", "c"]
is_fidelity: fals
default: "c"
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
search_space:
param_float1:
lower: 0.00001
upper: 0.1
default: 0.001
log: false
is_fidelity: truee
7 changes: 7 additions & 0 deletions tests/test_yaml_search_space/not_boolean_type_log_config.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
search_space:
param_float1:
lower: 0.00001
upper: 0.1
default: 0.001
log: falsee
is_fidelity: true
41 changes: 40 additions & 1 deletion tests/test_yaml_search_space/test_search_space.py
Original file line number Diff line number Diff line change
Expand Up @@ -109,9 +109,48 @@ def test_yaml_file_including_not_allowed_parameter_keys():


@pytest.mark.neps_api
def test_yaml_file_default_parameter_in_range():
def test_yaml_file_default_parameter_not_in_range():
"""Test if the default value outside the specified range is
correctly identified and handled."""
with pytest.raises(SearchSpaceFromYamlFileError) as excinfo:
pipeline_space_from_yaml(BASE_PATH + "default_not_in_range_config.yaml")
assert excinfo.value.exception_type == "ValueError"


@pytest.mark.neps_api
def test_float_log_not_boolean():
"""Test if an exception is raised when the 'log' attribute is not a boolean."""
with pytest.raises(SearchSpaceFromYamlFileError) as excinfo:
pipeline_space_from_yaml(BASE_PATH + "not_boolean_type_log_config.yaml")
assert excinfo.value.exception_type == "TypeError"


@pytest.mark.neps_api
def test_float_is_fidelity_not_boolean():
"""Test if an exception is raised when for FloatParameter the 'is_fidelity'
attribute is not a boolean."""
with pytest.raises(SearchSpaceFromYamlFileError) as excinfo:
pipeline_space_from_yaml(
BASE_PATH + "not_boolean_type_is_fidelity_float_config.yaml"
)
assert excinfo.value.exception_type == "TypeError"


@pytest.mark.neps_api
def test_cat_is_fidelity_not_boolean():
"""Test if an exception is raised when for CategoricalParameter the 'is_fidelity'
attribute is not boolean."""
with pytest.raises(SearchSpaceFromYamlFileError) as excinfo:
pipeline_space_from_yaml(
BASE_PATH + "not_boolean_type_is_fidelity_cat_config.yaml"
)
assert excinfo.value.exception_type == "TypeError"


@pytest.mark.neps_api
def test_categorical_default_value_not_in_choices():
"""Test if a ValueError is raised when the default value is not in the choices
for a CategoricalParameter."""
with pytest.raises(SearchSpaceFromYamlFileError) as excinfo:
pipeline_space_from_yaml(BASE_PATH + "default_value_not_in_choices_config.yaml")
assert excinfo.value.exception_type == "ValueError"

0 comments on commit 300b5a3

Please sign in to comment.