Source code for smac.facade.hyperparameter_optimization_facade

from __future__ import annotations

from ConfigSpace import Configuration

from smac.acquisition.function.expected_improvement import EI
from smac.acquisition.maximizer.local_and_random_search import (
    LocalAndSortedRandomSearch,
)
from smac.facade.abstract_facade import AbstractFacade
from smac.initial_design.sobol_design import SobolInitialDesign
from smac.intensifier.intensifier import Intensifier
from smac.model.random_forest.random_forest import RandomForest
from smac.multi_objective.aggregation_strategy import MeanAggregationStrategy
from smac.random_design.probability_design import ProbabilityRandomDesign
from smac.runhistory.encoder.log_scaled_encoder import RunHistoryLogScaledEncoder
from smac.scenario import Scenario

__copyright__ = "Copyright 2022, automl.org"
__license__ = "3-clause BSD"


[docs]class HyperparameterOptimizationFacade(AbstractFacade):
[docs] @staticmethod def get_model( # type: ignore scenario: Scenario, *, n_trees: int = 10, ratio_features: float = 1.0, min_samples_split: int = 2, min_samples_leaf: int = 1, max_depth: int = 2**20, bootstrapping: bool = True, ) -> RandomForest: """Returns a random forest as surrogate model. Parameters ---------- n_trees : int, defaults to 10 The number of trees in the random forest. ratio_features : float, defaults to 5.0 / 6.0 The ratio of features that are considered for splitting. min_samples_split : int, defaults to 3 The minimum number of data points to perform a split. min_samples_leaf : int, defaults to 3 The minimum number of data points in a leaf. max_depth : int, defaults to 20 The maximum depth of a single tree. bootstrapping : bool, defaults to True Enables bootstrapping. """ return RandomForest( log_y=True, n_trees=n_trees, bootstrapping=bootstrapping, ratio_features=ratio_features, min_samples_split=min_samples_split, min_samples_leaf=min_samples_leaf, max_depth=max_depth, configspace=scenario.configspace, instance_features=scenario.instance_features, seed=scenario.seed, )
[docs] @staticmethod def get_acquisition_function( # type: ignore scenario: Scenario, *, xi: float = 0.0, ) -> EI: """Returns an Expected Improvement acquisition function. Parameters ---------- scenario : Scenario xi : float, defaults to 0.0 Controls the balance between exploration and exploitation of the acquisition function. """ return EI(xi=xi, log=True)
[docs] @staticmethod def get_acquisition_maximizer( # type: ignore scenario: Scenario, *, challengers: int = 10000, local_search_iterations: int = 10, ) -> LocalAndSortedRandomSearch: """Returns local and sorted random search as acquisition maximizer. Warning ------- If you experience RAM issues, try to reduce the number of challengers. Parameters ---------- challengers : int, defaults to 10000 Number of challengers. local_search_iterations: int, defauts to 10 Number of local search iterations. """ optimizer = LocalAndSortedRandomSearch( scenario.configspace, challengers=challengers, local_search_iterations=local_search_iterations, seed=scenario.seed, ) return optimizer
[docs] @staticmethod def get_intensifier( # type: ignore scenario: Scenario, *, min_challenger: int = 1, min_config_calls: int = 1, max_config_calls: int = 3, intensify_percentage: float = 1e-10, ) -> Intensifier: """Returns ``Intensifier`` as intensifier. Uses the default configuration for ``race_against``. Parameters ---------- scenario : Scenario min_config_calls : int, defaults to 1 Minimum number of trials per config (summed over all calls to intensify). max_config_calls : int, defaults to 1 Maximum number of trials per config (summed over all calls to intensify). min_challenger : int, defaults to 3 Minimal number of challengers to be considered (even if time_bound is exhausted earlier). intensify_percentage : float, defaults to 1e-10 How much percentage of the time should configurations be intensified (evaluated on higher budgets or more instances). This parameter is accessed in the SMBO class. """ intensifier = Intensifier( scenario=scenario, min_challenger=min_challenger, race_against=scenario.configspace.get_default_configuration(), min_config_calls=min_config_calls, max_config_calls=max_config_calls, intensify_percentage=intensify_percentage, ) return intensifier
[docs] @staticmethod def get_initial_design( # type: ignore scenario: Scenario, *, n_configs: int | None = None, n_configs_per_hyperparamter: int = 10, max_ratio: float = 0.1, additional_configs: list[Configuration] = [], ) -> SobolInitialDesign: """Returns a Sobol design instance. Parameters ---------- scenario : Scenario n_configs : int | None, defaults to None Number of initial configurations (disables the arguments ``n_configs_per_hyperparameter``). n_configs_per_hyperparameter: int, defaults to 10 Number of initial configurations per hyperparameter. For example, if my configuration space covers five hyperparameters and ``n_configs_per_hyperparameter`` is set to 10, then 50 initial configurations will be samples. max_ratio: float, defaults to 0.1 Use at most ``scenario.n_trials`` * ``max_ratio`` number of configurations in the initial design. Additional configurations are not affected by this parameter. additional_configs: list[Configuration], defaults to [] Adds additional configurations to the initial design. """ return SobolInitialDesign( scenario=scenario, n_configs=n_configs, n_configs_per_hyperparameter=n_configs_per_hyperparamter, max_ratio=max_ratio, additional_configs=additional_configs, )
[docs] @staticmethod def get_random_design( # type: ignore scenario: Scenario, *, probability: float = 0.2, ) -> ProbabilityRandomDesign: """Returns ``ProbabilityRandomDesign`` for interleaving configurations. Parameters ---------- probability : float, defaults to 0.2 Probability that a configuration will be drawn at random. """ return ProbabilityRandomDesign(probability=probability)
[docs] @staticmethod def get_multi_objective_algorithm( # type: ignore scenario: Scenario, *, objective_weights: list[float] | None = None, ) -> MeanAggregationStrategy: """Returns the mean aggregation strategy for the multi objective algorithm. Parameters ---------- scenario : Scenario objective_weights : list[float] | None, defaults to None Weights for an weighted average. Must be of the same length as the number of objectives. """ return MeanAggregationStrategy( scenario=scenario, objective_weights=objective_weights, )
[docs] @staticmethod def get_runhistory_encoder( # type: ignore scenario: Scenario, ) -> RunHistoryLogScaledEncoder: """Returns a log scaled runhistory encoder. That means that costs are log scaled before training the surrogate model. """ return RunHistoryLogScaledEncoder(scenario)