From dbe2be24cc33f281c271aa36be3ebcbb0c0d8a56 Mon Sep 17 00:00:00 2001 From: kajal-jotwani Date: Fri, 20 Feb 2026 22:13:24 +0530 Subject: [PATCH 01/13] Add LightGBM Experiment integration --- .../experiment/integrations/__init__.py | 2 + .../integrations/lightgbm_experiment.py | 64 +++++++++++++++++++ 2 files changed, 66 insertions(+) create mode 100644 src/hyperactive/experiment/integrations/lightgbm_experiment.py diff --git a/src/hyperactive/experiment/integrations/__init__.py b/src/hyperactive/experiment/integrations/__init__.py index c302e25a..351d97f5 100644 --- a/src/hyperactive/experiment/integrations/__init__.py +++ b/src/hyperactive/experiment/integrations/__init__.py @@ -2,6 +2,7 @@ # copyright: hyperactive developers, MIT License (see LICENSE file) from hyperactive.experiment.integrations.sklearn_cv import SklearnCvExperiment +from hyperactive.experiment.integrations.lightgbm_experiment import LightGBMExperiment from hyperactive.experiment.integrations.skpro_probareg import ( SkproProbaRegExperiment, ) @@ -21,4 +22,5 @@ "SktimeClassificationExperiment", "SktimeForecastingExperiment", "TorchExperiment", + "LightGBMExperiment", ] diff --git a/src/hyperactive/experiment/integrations/lightgbm_experiment.py b/src/hyperactive/experiment/integrations/lightgbm_experiment.py new file mode 100644 index 00000000..bfc551a9 --- /dev/null +++ b/src/hyperactive/experiment/integrations/lightgbm_experiment.py @@ -0,0 +1,64 @@ +"""Experiment adapter for LightGBM cross-validation experiments.""" + +# copyright: hyperactive developers, MIT License (see LICENSE file) + +from hyperactive.experiment.integrations.sklearn_cv import SklearnCvExperiment + + +class LightGBMExperiment(SklearnCvExperiment): + """Experiment adapter for LightGBM cross-validation experiments. + + Thin wrapper around SklearnCvExperiment for LightGBM estimators. + + LightGBM estimators follow the sklearn API, so this class does not + add new functionality beyond SklearnCvExperiment. It exists for + discoverability and explicit LightGBM support. + """ + + _tags = { + "python_dependencies": "lightgbm", + } + + @classmethod + def get_test_params(cls, parameter_set="default"): + """Return testing parameter settings for the estimator.""" + from skbase.utils.dependencies import _check_soft_dependencies + + if not _check_soft_dependencies("lightgbm", severity="none"): + return [] + + from sklearn.datasets import load_iris, load_diabetes + from lightgbm import LGBMClassifier, LGBMRegressor + + # Classification test case + X, y = load_iris(return_X_y=True) + params0 = { + "estimator": LGBMClassifier(n_estimators=10), + "X": X, + "y": y, + "cv": 2, + } + + # Regression test case + X, y = load_diabetes(return_X_y=True) + params1 = { + "estimator": LGBMRegressor(n_estimators=10), + "X": X, + "y": y, + "cv": 2, + } + + return [params0, params1] + + @classmethod + def _get_score_params(cls): + """Return parameter settings for score/evaluate tests.""" + from skbase.utils.dependencies import _check_soft_dependencies + + if not _check_soft_dependencies("lightgbm", severity="none"): + return [] + + val0 = {"n_estimators": 5, "max_depth": 2} + val1 = {"n_estimators": 5, "max_depth": 2} + + return [val0, val1] \ No newline at end of file From 8789a25469464e3203c901c07c9ef1b448955c19 Mon Sep 17 00:00:00 2001 From: kajal-jotwani Date: Fri, 6 Mar 2026 10:40:58 +0530 Subject: [PATCH 02/13] pre-commit fixes --- src/hyperactive/experiment/integrations/__init__.py | 2 +- .../experiment/integrations/lightgbm_experiment.py | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/hyperactive/experiment/integrations/__init__.py b/src/hyperactive/experiment/integrations/__init__.py index 351d97f5..f4dba126 100644 --- a/src/hyperactive/experiment/integrations/__init__.py +++ b/src/hyperactive/experiment/integrations/__init__.py @@ -1,8 +1,8 @@ """Integrations with packages for tuning.""" # copyright: hyperactive developers, MIT License (see LICENSE file) -from hyperactive.experiment.integrations.sklearn_cv import SklearnCvExperiment from hyperactive.experiment.integrations.lightgbm_experiment import LightGBMExperiment +from hyperactive.experiment.integrations.sklearn_cv import SklearnCvExperiment from hyperactive.experiment.integrations.skpro_probareg import ( SkproProbaRegExperiment, ) diff --git a/src/hyperactive/experiment/integrations/lightgbm_experiment.py b/src/hyperactive/experiment/integrations/lightgbm_experiment.py index bfc551a9..2b5fcc0a 100644 --- a/src/hyperactive/experiment/integrations/lightgbm_experiment.py +++ b/src/hyperactive/experiment/integrations/lightgbm_experiment.py @@ -27,8 +27,8 @@ def get_test_params(cls, parameter_set="default"): if not _check_soft_dependencies("lightgbm", severity="none"): return [] - from sklearn.datasets import load_iris, load_diabetes from lightgbm import LGBMClassifier, LGBMRegressor + from sklearn.datasets import load_diabetes, load_iris # Classification test case X, y = load_iris(return_X_y=True) @@ -61,4 +61,4 @@ def _get_score_params(cls): val0 = {"n_estimators": 5, "max_depth": 2} val1 = {"n_estimators": 5, "max_depth": 2} - return [val0, val1] \ No newline at end of file + return [val0, val1] From 16e7b4f04da53219c8df46f56afd153947e5ec57 Mon Sep 17 00:00:00 2001 From: kajal-jotwani Date: Thu, 12 Mar 2026 13:23:55 +0530 Subject: [PATCH 03/13] add docs and tests --- .../_snippets/user_guide/integrations.py | 35 +++++++++++++ .../experiments_integrations.rst | 13 ++++- docs/source/user_guide/integrations.rst | 43 +++++++++++++++- src/hyperactive/base/tests/test_lightgbm.py | 49 +++++++++++++++++++ 4 files changed, 138 insertions(+), 2 deletions(-) create mode 100644 src/hyperactive/base/tests/test_lightgbm.py diff --git a/docs/source/_snippets/user_guide/integrations.py b/docs/source/_snippets/user_guide/integrations.py index 5b9a0507..2eec0499 100644 --- a/docs/source/_snippets/user_guide/integrations.py +++ b/docs/source/_snippets/user_guide/integrations.py @@ -226,6 +226,41 @@ def configure_optimizers(self): best_params = optimizer.solve() # [end:pytorch_lightning] +# [start:lightgbm_experiment] +from lightgbm import LGBMClassifier +from sklearn.datasets import load_iris + +from hyperactive.experiment.integrations import LightGBMExperiment +from hyperactive.opt.gfo import BayesianOptimizer + +# Load data +X, y = load_iris(return_X_y=True) + +# Create the experiment +experiment = LightGBMExperiment( + estimator=LGBMClassifier(), + X=X, + y=y, + cv=3, +) + +# Define search space +search_space = { + "n_estimators": [50, 100, 200], + "max_depth": [3, 5, 7, -1], + "learning_rate": [0.01, 0.05, 0.1, 0.2], +} + +# Optimize +optimizer = BayesianOptimizer( + search_space=search_space, + n_iter=10, + experiment=experiment, +) +best_params = optimizer.solve() +print(f"Best parameters: {best_params}") +# [end:lightgbm_experiment] + # --- Runnable test code below --- if __name__ == "__main__": diff --git a/docs/source/api_reference/experiments_integrations.rst b/docs/source/api_reference/experiments_integrations.rst index 913e249a..4cca69ce 100644 --- a/docs/source/api_reference/experiments_integrations.rst +++ b/docs/source/api_reference/experiments_integrations.rst @@ -7,7 +7,7 @@ The :mod:`hyperactive.experiment.integrations` module contains experiment classe for integration with machine learning frameworks. These experiments provide seamless hyperparameter optimization for scikit-learn, -sktime, skpro, and PyTorch Lightning models. +sktime, skpro, PyTorch Lightning, and LightGBM models. Scikit-Learn ------------ @@ -55,3 +55,14 @@ Experiments for PyTorch Lightning models. :template: class.rst TorchExperiment + +LightGBM +-------- + +Cross-validation experiments for LightGBM estimators. + +.. autosummary:: + :toctree: auto_generated/ + :template: class.rst + + LightGBMExperiment diff --git a/docs/source/user_guide/integrations.rst b/docs/source/user_guide/integrations.rst index cf0bc2f9..07768d88 100644 --- a/docs/source/user_guide/integrations.rst +++ b/docs/source/user_guide/integrations.rst @@ -7,7 +7,7 @@ Framework Integrations Hyperactive integrates with popular ML frameworks, providing drop-in replacements for tools like ``GridSearchCV``. Each ML framework has its own conventions for training and evaluation. The integration classes handle cross-validation setup, scoring metrics, and parameter translation, so -you can use any optimizer with scikit-learn, sktime, skpro, or PyTorch models. +you can use any optimizer with scikit-learn, sktime, skpro, PyTorch, or LightGBM models. ---- @@ -53,6 +53,15 @@ Supported Frameworks Deep learning models + .. grid-item-card:: LightGBM + :class-card: sd-border-info + :link: #lightgbm-integration + :link-type: url + + **LightGBMExperiment** + + Gradient boosting models + ---- Quick Reference @@ -86,6 +95,10 @@ Quick Reference - ``TorchExperiment`` - Deep learning models - ``[all_extras]`` + * - LightGBM + - ``LightGBMExperiment`` + - Classification, regression + - ``[lightgbm]`` ---- @@ -237,6 +250,34 @@ For deep learning hyperparameter optimization with PyTorch Lightning: ---- +LightGBM Integration +-------------------- + +For gradient boosting hyperparameter optimization with LightGBM: + +.. note:: + + Requires ``pip install lightgbm`` + +.. grid:: 1 + :gutter: 0 + + .. grid-item:: + :class: sd-bg-light sd-pt-3 sd-pb-1 sd-ps-3 sd-pe-3 sd-rounded-3 + + **Key Features** + + - Optimize LightGBM classifiers and regressors + - LightGBM follows the sklearn API, so cross-validation works out of the box + - Supports all LightGBM hyperparameters (``n_estimators``, ``max_depth``, ``learning_rate``, etc.) + +.. literalinclude:: ../_snippets/user_guide/integrations.py + :language: python + :start-after: # [start:lightgbm_experiment] + :end-before: # [end:lightgbm_experiment] + +---- + Tips ---- diff --git a/src/hyperactive/base/tests/test_lightgbm.py b/src/hyperactive/base/tests/test_lightgbm.py new file mode 100644 index 00000000..9a981744 --- /dev/null +++ b/src/hyperactive/base/tests/test_lightgbm.py @@ -0,0 +1,49 @@ +"""Integration test for end-to-end usage of optimizer with LightGBM experiment.""" +# copyright: hyperactive developers, MIT License (see LICENSE file) + + + +def test_endtoend_lightgbm(): + """Test end-to-end usage of HillClimbing optimizer with LightGBM experiment.""" + from skbase.utils.dependencies import _check_soft_dependencies + + if not _check_soft_dependencies("lightgbm", severity="none"): + return None + + # define the experiment + from lightgbm import LGBMClassifier + from sklearn.datasets import load_iris + + from hyperactive.experiment.integrations import LightGBMExperiment + + X, y = load_iris(return_X_y=True) + + lgbm_exp = LightGBMExperiment( + estimator=LGBMClassifier(n_estimators=10, verbosity=-1), + X=X, + y=y, + cv=2, + ) + + # set up the HillClimbing optimizer + import numpy as np + + from hyperactive.opt import HillClimbing + + hillclimbing_config = { + "search_space": { + "n_estimators": np.array([5, 10, 20]), + "max_depth": np.array([2, 3, 5]), + }, + "n_iter": 10, + } + hill_climbing = HillClimbing(**hillclimbing_config, experiment=lgbm_exp) + + # run the HillClimbing optimizer + hill_climbing.solve() + + best_params = hill_climbing.best_params_ + assert best_params is not None, "Best parameters should not be None" + assert isinstance(best_params, dict), "Best parameters should be a dictionary" + assert "n_estimators" in best_params, "Best parameters should contain 'n_estimators'" + assert "max_depth" in best_params, "Best parameters should contain 'max_depth'" \ No newline at end of file From 85906db4acca76f6fe067b97d21eed54af58ce38 Mon Sep 17 00:00:00 2001 From: kajal-jotwani Date: Thu, 12 Mar 2026 18:09:14 +0530 Subject: [PATCH 04/13] fix lint --- src/hyperactive/base/tests/test_lightgbm.py | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/src/hyperactive/base/tests/test_lightgbm.py b/src/hyperactive/base/tests/test_lightgbm.py index 9a981744..078a2b65 100644 --- a/src/hyperactive/base/tests/test_lightgbm.py +++ b/src/hyperactive/base/tests/test_lightgbm.py @@ -2,7 +2,6 @@ # copyright: hyperactive developers, MIT License (see LICENSE file) - def test_endtoend_lightgbm(): """Test end-to-end usage of HillClimbing optimizer with LightGBM experiment.""" from skbase.utils.dependencies import _check_soft_dependencies @@ -45,5 +44,7 @@ def test_endtoend_lightgbm(): best_params = hill_climbing.best_params_ assert best_params is not None, "Best parameters should not be None" assert isinstance(best_params, dict), "Best parameters should be a dictionary" - assert "n_estimators" in best_params, "Best parameters should contain 'n_estimators'" - assert "max_depth" in best_params, "Best parameters should contain 'max_depth'" \ No newline at end of file + assert ( + "n_estimators" in best_params + ), "Best parameters should contain 'n_estimators'" + assert "max_depth" in best_params, "Best parameters should contain 'max_depth'" From e4bf316fe8556bb25cb68ca60677263a1575762e Mon Sep 17 00:00:00 2001 From: Simon Blanke Date: Thu, 23 Apr 2026 20:26:13 +0200 Subject: [PATCH 05/13] set verb to -1 --- docs/source/_snippets/user_guide/integrations.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/source/_snippets/user_guide/integrations.py b/docs/source/_snippets/user_guide/integrations.py index 2eec0499..7e07ff1b 100644 --- a/docs/source/_snippets/user_guide/integrations.py +++ b/docs/source/_snippets/user_guide/integrations.py @@ -238,7 +238,7 @@ def configure_optimizers(self): # Create the experiment experiment = LightGBMExperiment( - estimator=LGBMClassifier(), + estimator=LGBMClassifier(verbosity=-1), X=X, y=y, cv=3, From c2dec2c14935fa32348d00e7cff286331dba994e Mon Sep 17 00:00:00 2001 From: Simon Blanke Date: Thu, 23 Apr 2026 20:26:31 +0200 Subject: [PATCH 06/13] remove dep. --- docs/source/user_guide/integrations.rst | 4 ---- 1 file changed, 4 deletions(-) diff --git a/docs/source/user_guide/integrations.rst b/docs/source/user_guide/integrations.rst index 07768d88..8c9ec90d 100644 --- a/docs/source/user_guide/integrations.rst +++ b/docs/source/user_guide/integrations.rst @@ -95,10 +95,6 @@ Quick Reference - ``TorchExperiment`` - Deep learning models - ``[all_extras]`` - * - LightGBM - - ``LightGBMExperiment`` - - Classification, regression - - ``[lightgbm]`` ---- From 8e99f8b432d4cfd70292edd3e8dd8aadaf68e4d2 Mon Sep 17 00:00:00 2001 From: Simon Blanke Date: Thu, 23 Apr 2026 20:27:22 +0200 Subject: [PATCH 07/13] add docstring + fix tests --- .../integrations/lightgbm_experiment.py | 60 +++++++++++++++---- 1 file changed, 47 insertions(+), 13 deletions(-) diff --git a/src/hyperactive/experiment/integrations/lightgbm_experiment.py b/src/hyperactive/experiment/integrations/lightgbm_experiment.py index 2b5fcc0a..f80760d3 100644 --- a/src/hyperactive/experiment/integrations/lightgbm_experiment.py +++ b/src/hyperactive/experiment/integrations/lightgbm_experiment.py @@ -8,14 +8,52 @@ class LightGBMExperiment(SklearnCvExperiment): """Experiment adapter for LightGBM cross-validation experiments. - Thin wrapper around SklearnCvExperiment for LightGBM estimators. - - LightGBM estimators follow the sklearn API, so this class does not - add new functionality beyond SklearnCvExperiment. It exists for - discoverability and explicit LightGBM support. + Thin wrapper around ``SklearnCvExperiment`` for LightGBM estimators. + LightGBM's sklearn-compatible API (``LGBMClassifier``, ``LGBMRegressor``) + works without adaptation. This class exists for discoverability, explicit + soft-dependency tracking via the ``python_dependencies`` tag, and as an + extension point for future LightGBM-specific behavior. + + Parameters + ---------- + estimator : LGBMClassifier or LGBMRegressor + The LightGBM estimator to evaluate. Any sklearn-compatible estimator + is accepted, but LightGBM estimators are the intended use case. + X : array-like, shape (n_samples, n_features) + Input data. + y : array-like, shape (n_samples,) + Target values. + scoring : callable or str, default=None + Scoring function. Defaults follow ``SklearnCvExperiment`` conventions: + ``accuracy_score`` for classifiers, ``mean_squared_error`` for + regressors. + cv : int or cross-validation generator, default=KFold(n_splits=3, shuffle=True) + Cross-validation strategy. + + Notes + ----- + LightGBM prints training logs to stdout by default. Pass + ``verbosity=-1`` to the estimator constructor to suppress this output. + + For all remaining parameter details see ``SklearnCvExperiment``. + + Examples + -------- + >>> from hyperactive.experiment.integrations import LightGBMExperiment + >>> from lightgbm import LGBMClassifier + >>> from sklearn.datasets import load_iris + >>> X, y = load_iris(return_X_y=True) + >>> exp = LightGBMExperiment( + ... estimator=LGBMClassifier(verbosity=-1), + ... X=X, + ... y=y, + ... ) + >>> params = {"n_estimators": 50, "max_depth": 3} + >>> score, metadata = exp.score(params) """ _tags = { + "authors": ["kajal-jotwani"], "python_dependencies": "lightgbm", } @@ -30,19 +68,17 @@ def get_test_params(cls, parameter_set="default"): from lightgbm import LGBMClassifier, LGBMRegressor from sklearn.datasets import load_diabetes, load_iris - # Classification test case X, y = load_iris(return_X_y=True) params0 = { - "estimator": LGBMClassifier(n_estimators=10), + "estimator": LGBMClassifier(n_estimators=10, verbosity=-1), "X": X, "y": y, "cv": 2, } - # Regression test case X, y = load_diabetes(return_X_y=True) params1 = { - "estimator": LGBMRegressor(n_estimators=10), + "estimator": LGBMRegressor(n_estimators=10, verbosity=-1), "X": X, "y": y, "cv": 2, @@ -58,7 +94,5 @@ def _get_score_params(cls): if not _check_soft_dependencies("lightgbm", severity="none"): return [] - val0 = {"n_estimators": 5, "max_depth": 2} - val1 = {"n_estimators": 5, "max_depth": 2} - - return [val0, val1] + score_params = {"n_estimators": 5, "max_depth": 2} + return [score_params, score_params] From 194418dd9e633c0c6221a300507ddd0b4c000154 Mon Sep 17 00:00:00 2001 From: Simon Blanke Date: Thu, 23 Apr 2026 20:27:37 +0200 Subject: [PATCH 08/13] add LightGBMExperiment + rearange --- src/hyperactive/experiment/integrations/__init__.py | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/src/hyperactive/experiment/integrations/__init__.py b/src/hyperactive/experiment/integrations/__init__.py index f4dba126..a143a89c 100644 --- a/src/hyperactive/experiment/integrations/__init__.py +++ b/src/hyperactive/experiment/integrations/__init__.py @@ -2,6 +2,9 @@ # copyright: hyperactive developers, MIT License (see LICENSE file) from hyperactive.experiment.integrations.lightgbm_experiment import LightGBMExperiment +from hyperactive.experiment.integrations.skforecast_forecasting import ( + SkforecastExperiment, +) from hyperactive.experiment.integrations.sklearn_cv import SklearnCvExperiment from hyperactive.experiment.integrations.skpro_probareg import ( SkproProbaRegExperiment, @@ -17,10 +20,11 @@ ) __all__ = [ + "LightGBMExperiment", + "SkforecastExperiment", "SklearnCvExperiment", "SkproProbaRegExperiment", "SktimeClassificationExperiment", "SktimeForecastingExperiment", "TorchExperiment", - "LightGBMExperiment", ] From 0647911432865bb68e42a72694e6a93736931dc4 Mon Sep 17 00:00:00 2001 From: Simon Blanke Date: Thu, 23 Apr 2026 20:27:56 +0200 Subject: [PATCH 09/13] move test --- src/hyperactive/base/tests/test_endtoend.py | 48 ++++++++++++++++++++ src/hyperactive/base/tests/test_lightgbm.py | 50 --------------------- 2 files changed, 48 insertions(+), 50 deletions(-) delete mode 100644 src/hyperactive/base/tests/test_lightgbm.py diff --git a/src/hyperactive/base/tests/test_endtoend.py b/src/hyperactive/base/tests/test_endtoend.py index 73b71ba2..b01ae8c7 100644 --- a/src/hyperactive/base/tests/test_endtoend.py +++ b/src/hyperactive/base/tests/test_endtoend.py @@ -47,3 +47,51 @@ def test_endtoend_hillclimbing(): assert isinstance(best_params, dict), "Best parameters should be a dictionary" assert "C" in best_params, "Best parameters should contain 'C'" assert "gamma" in best_params, "Best parameters should contain 'gamma'" + + +def test_endtoend_lightgbm(): + """Test end-to-end usage of HillClimbing optimizer with LightGBM experiment.""" + from skbase.utils.dependencies import _check_soft_dependencies + + if not _check_soft_dependencies("lightgbm", severity="none"): + return None + + # 1. define the experiment + from lightgbm import LGBMClassifier + from sklearn.datasets import load_iris + + from hyperactive.experiment.integrations import LightGBMExperiment + + X, y = load_iris(return_X_y=True) + + lgbm_exp = LightGBMExperiment( + estimator=LGBMClassifier(n_estimators=10, verbosity=-1), + X=X, + y=y, + cv=2, + ) + + # 2. set up the HillClimbing optimizer + import numpy as np + + from hyperactive.opt import HillClimbing + + hillclimbing_config = { + "search_space": { + "n_estimators": np.array([5, 10, 20]), + "max_depth": np.array([2, 3, 5]), + }, + "n_iter": 10, + } + hill_climbing = HillClimbing(**hillclimbing_config, experiment=lgbm_exp) + + # 3. run the HillClimbing optimizer + hill_climbing.solve() + + best_params = hill_climbing.best_params_ + assert best_params is not None, "Best parameters should not be None" + assert isinstance(best_params, dict), "Best parameters should be a dictionary" + assert ( + "n_estimators" in best_params + ), "Best parameters should contain 'n_estimators'" + assert "max_depth" in best_params, "Best parameters should contain 'max_depth'" diff --git a/src/hyperactive/base/tests/test_lightgbm.py b/src/hyperactive/base/tests/test_lightgbm.py deleted file mode 100644 index 078a2b65..00000000 --- a/src/hyperactive/base/tests/test_lightgbm.py +++ /dev/null @@ -1,50 +0,0 @@ -"""Integration test for end-to-end usage of optimizer with LightGBM experiment.""" -# copyright: hyperactive developers, MIT License (see LICENSE file) - - -def test_endtoend_lightgbm(): - """Test end-to-end usage of HillClimbing optimizer with LightGBM experiment.""" - from skbase.utils.dependencies import _check_soft_dependencies - - if not _check_soft_dependencies("lightgbm", severity="none"): - return None - - # define the experiment - from lightgbm import LGBMClassifier - from sklearn.datasets import load_iris - - from hyperactive.experiment.integrations import LightGBMExperiment - - X, y = load_iris(return_X_y=True) - - lgbm_exp = LightGBMExperiment( - estimator=LGBMClassifier(n_estimators=10, verbosity=-1), - X=X, - y=y, - cv=2, - ) - - # set up the HillClimbing optimizer - import numpy as np - - from hyperactive.opt import HillClimbing - - hillclimbing_config = { - "search_space": { - "n_estimators": np.array([5, 10, 20]), - "max_depth": np.array([2, 3, 5]), - }, - "n_iter": 10, - } - hill_climbing = HillClimbing(**hillclimbing_config, experiment=lgbm_exp) - - # run the HillClimbing optimizer - hill_climbing.solve() - - best_params = hill_climbing.best_params_ - assert best_params is not None, "Best parameters should not be None" - assert isinstance(best_params, dict), "Best parameters should be a dictionary" - assert ( - "n_estimators" in best_params - ), "Best parameters should contain 'n_estimators'" - assert "max_depth" in best_params, "Best parameters should contain 'max_depth'" From e4eee1d564face0d3716cbcfad03071a595c975f Mon Sep 17 00:00:00 2001 From: Simon Blanke Date: Thu, 23 Apr 2026 20:29:11 +0200 Subject: [PATCH 10/13] add 'lightgbm' to all_extras --- pyproject.toml | 1 + 1 file changed, 1 insertion(+) diff --git a/pyproject.toml b/pyproject.toml index 21e3413c..e33bcb34 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -99,6 +99,7 @@ all_extras = [ "optuna<5", "cmaes", # Required for CmaEsOptimizer (optuna's CMA-ES sampler) "lightning", + "lightgbm", ] From 3a544ae6745bab23ae29a582506b03937343aa55 Mon Sep 17 00:00:00 2001 From: Simon Blanke Date: Thu, 23 Apr 2026 20:48:20 +0200 Subject: [PATCH 11/13] remove wrong import --- src/hyperactive/experiment/integrations/__init__.py | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/src/hyperactive/experiment/integrations/__init__.py b/src/hyperactive/experiment/integrations/__init__.py index a143a89c..73878f11 100644 --- a/src/hyperactive/experiment/integrations/__init__.py +++ b/src/hyperactive/experiment/integrations/__init__.py @@ -1,10 +1,8 @@ """Integrations with packages for tuning.""" + # copyright: hyperactive developers, MIT License (see LICENSE file) from hyperactive.experiment.integrations.lightgbm_experiment import LightGBMExperiment -from hyperactive.experiment.integrations.skforecast_forecasting import ( - SkforecastExperiment, -) from hyperactive.experiment.integrations.sklearn_cv import SklearnCvExperiment from hyperactive.experiment.integrations.skpro_probareg import ( SkproProbaRegExperiment, @@ -21,7 +19,6 @@ __all__ = [ "LightGBMExperiment", - "SkforecastExperiment", "SklearnCvExperiment", "SkproProbaRegExperiment", "SktimeClassificationExperiment", From 319a3f723e1f4b5f4bd03b08f893cccd13d50d08 Mon Sep 17 00:00:00 2001 From: Simon Blanke Date: Thu, 23 Apr 2026 20:57:10 +0200 Subject: [PATCH 12/13] add lightgbm fix for macos --- .github/workflows/test.yml | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index b8a90b68..4b622892 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -361,6 +361,10 @@ jobs: with: python-version: ${{ matrix.python-version }} + - name: Install libomp (macOS) + if: runner.os == 'macOS' + run: brew install libomp + - name: Install dependencies run: | python -m pip install --no-cache-dir --upgrade pip From c7d628b83c932232639f1a0b60d487ed4b2d79b9 Mon Sep 17 00:00:00 2001 From: Simon Blanke Date: Fri, 24 Apr 2026 06:17:16 +0200 Subject: [PATCH 13/13] remove lightgbm tests that run infinitly in the CI --- .github/workflows/test.yml | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index 4b622892..a35c6762 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -361,16 +361,16 @@ jobs: with: python-version: ${{ matrix.python-version }} - - name: Install libomp (macOS) - if: runner.os == 'macOS' - run: brew install libomp - - name: Install dependencies run: | python -m pip install --no-cache-dir --upgrade pip python -m pip install --no-cache-dir build make install-all-extras-for-test + - name: Remove lightgbm on macOS (native lib requires libomp, tests hang) + if: runner.os == 'macOS' + run: python -m pip uninstall -y lightgbm + - name: Show dependencies run: python -m pip list