Customize Exploration StrategyΒΆ

If users want to innovate a new exploration strategy, they can easily customize a new one following the interface provided by NNI. Specifically, users should inherit the base strategy class BaseStrategy, then implement the member function run. This member function takes base_model and applied_mutators as its input arguments. It can simply apply the user specified mutators in applied_mutators onto base_model to generate a new model. When a mutator is applied, it should be bound with a sampler (e.g., RandomSampler). Every sampler implements the choice function which chooses value(s) from candidate values. The choice functions invoked in mutators are executed with the sampler.

Below is a very simple random strategy, which makes the choices completely random.

from nni.retiarii import Sampler

class RandomSampler(Sampler):
    def choice(self, candidates, mutator, model, index):
        return random.choice(candidates)

class RandomStrategy(BaseStrategy):
    def __init__(self):
        self.random_sampler = RandomSampler()

    def run(self, base_model, applied_mutators):'stargety start...')
        while True:
            avail_resource = query_available_resources()
            if avail_resource > 0:
                model = base_model
      'apply mutators...')
      'mutators: %s', str(applied_mutators))
                for mutator in applied_mutators:
                    model = mutator.apply(model)
                # run models

You can find that this strategy does not know the search space beforehand, it passively makes decisions every time choice is invoked from mutators. If a strategy wants to know the whole search space before making any decision (e.g., TPE, SMAC), it can use dry_run function provided by Mutator to obtain the space. An example strategy can be found here.

After generating a new model, the strategy can use our provided APIs (e.g., submit_models, is_stopped_exec) to submit the model and get its reported results. More APIs can be found in API References.