Source code for pynol.learner.specification.surrogate_base

from abc import ABC, abstractmethod

import numpy as np


[docs]class SurrogateBase(ABC): """The abstract class defines the surrogate loss functions and surrogate gradient (if possible) for base-learners.""" def __init__(self): pass
[docs] @abstractmethod def compute_surrogate_base(self, variables): """Compute the surrogate loss functions and surrogate gradient (if possible) for base-learners.""" raise NotImplementedError()
[docs]class LinearSurrogateBase(SurrogateBase): """The class defines the linear surrogate loss function for base-learners.""" def __init__(self): pass
[docs] def compute_surrogate_base(self, variables): """Compute the surrogate loss functions and surrogate gradient (if possible) for base-learners. Replace original convex function :math:`f_t(x)` with .. math:: f'_t(x)=\langle \\nabla f_t(x_t),x - x_t \\rangle, for all base-learners, where :math:`x_t` is the submitted decision at round :math:`t`. Since the gradient of any decision for the linear function is :math:`\\nabla f_t(x_t)`, this method will return it also to reduce the gradient query complexity for base-learners. Args: variables (dict): intermediate variables of the learning process at current round. Returns: tuple: tuple contains: surrogate_func (Callable): Surrogate function for base-learners. \n surrogate_grad (numpy.ndarray): Surrogate gradient for base-learners. """ return lambda x: np.dot(x - variables['x'], variables['grad']), variables['grad']
[docs]class InnerSurrogateBase(SurrogateBase): """The class defines the inner surrogate loss function for base-learners.""" def __init__(self): pass
[docs] def compute_surrogate_base(self, variables): """Compute the surrogate loss functions and surrogate gradient (if possible) for base-learners. Replace original convex function :math:`f_t(x)` with .. math:: f'_t(x)=\langle \\nabla f_t(x_t), x \\rangle, for all base-learners, where :math:`x_t` is the submitted decision at round :math:`t`. Since the gradient of any decision for the inner function is :math:`\\nabla f_t(x_t)`, this method will return it also to reduce the gradient query complexity for base-learners. Args: variables (dict): intermediate variables of the learning process at current round. Returns: tuple: tuple contains: surrogate_func (Callable): Surrogate function for base-learners. \n surrogate_grad (numpy.ndarray): Surrogate gradient for base-learners. """ return lambda x: np.dot(x, variables['grad']), variables['grad']