easyvvuq.sampling.grid_sampler

A grid sampler

Useful for e.g. hyperparameter search. The "vary" dict contains the values that must be considered per (hyper)parameter, for instance:

vary = {"x1": [0.0, 0.5, 0.1],
        "x2 = [1, 3],
        "x3" = [True, False]}

The sampler will create a tensor grid using all specified 1D parameter values.

  1"""A grid sampler
  2
  3Useful for e.g. hyperparameter search. The "vary" dict contains the values
  4that must be considered per (hyper)parameter, for instance:
  5
  6    vary = {"x1": [0.0, 0.5, 0.1],
  7            "x2 = [1, 3],
  8            "x3" = [True, False]}
  9
 10The sampler will create a tensor grid using all specified 1D parameter
 11values.
 12"""
 13
 14__author__ = "Wouter Edeling"
 15__copyright__ = """
 16
 17    Copyright 2018 Robin A. Richardson, David W. Wright
 18
 19    This file is part of EasyVVUQ
 20
 21    EasyVVUQ is free software: you can redistribute it and/or modify
 22    it under the terms of the Lesser GNU General Public License as published by
 23    the Free Software Foundation, either version 3 of the License, or
 24    (at your option) any later version.
 25
 26    EasyVVUQ is distributed in the hope that it will be useful,
 27    but WITHOUT ANY WARRANTY; without even the implied warranty of
 28    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 29    Lesser GNU General Public License for more details.
 30
 31    You should have received a copy of the Lesser GNU General Public License
 32    along with this program.  If not, see <https://www.gnu.org/licenses/>.
 33
 34"""
 35__license__ = "LGPL"
 36
 37from itertools import product
 38import numpy as np
 39from .base import BaseSamplingElement  # , Vary
 40
 41
 42class Grid_Sampler(BaseSamplingElement, sampler_name="grid_sampler"):
 43
 44    def __init__(self, vary, count=0):
 45        """
 46        Initialize the grid sampler.
 47
 48        Parameters
 49        ----------
 50        vary : dict, or list of dicts
 51            A dictionary containing all 1D values for each parameter. For instance
 52            vary = {"x1": [0.0, 0.5. 1.0], "x2": [True, False]}. This will
 53            create a 2D tensor product of all (x1, x2) parameter combinations.
 54            If a list of vary dicts is specified, each vary dict will be treated
 55            independently to generate points. These dicts do not have to contain
 56            the same parameters. The tensor product points are stored in the 
 57            'points' list, with one tensor product per vary dict.
 58        count : int, optional
 59            Internal counter used to count the number of samples that have
 60            been executed. The default is 0.
 61
 62        Returns
 63        -------
 64        None.
 65
 66        """
 67        # allways add vary to list, even if only a single dict is specified
 68        if not isinstance(vary, list):
 69            vary = [vary]
 70
 71        self.vary = vary
 72        self.count = count
 73        self.points = []
 74
 75        # make sure all parameters are stored in a list or array, even
 76        # if they have only a single value
 77        for _vary in vary:
 78            for param in _vary.keys():
 79                if not isinstance(_vary[param], list) and not isinstance(_vary[param], np.ndarray):
 80                    vary[param] = [vary[param]]
 81
 82            # use dtype=object to allow for multiple different type (float, boolean etc)
 83            self.points.append(np.array(list(product(*list(_vary.values()))), dtype=object))
 84
 85        # the cumulative sizes of all ensembles generated by the vary dicts
 86        self.cumul_sizes = np.cumsum([points.shape[0] for points in self.points])
 87        # add a zero to the beginning (necessary in __next__ subroutine)
 88        self.cumul_sizes = np.insert(self.cumul_sizes, 0, 0)
 89
 90    def is_finite(self):
 91        return True
 92
 93    def n_samples(self):
 94        """Returns the number of samples in this sampler.
 95        """
 96        # return self.points.shape[0]
 97        return self.cumul_sizes[-1]
 98
 99    def get_param_names(self):
100        """
101        Get the names of all parameters that were varied.
102
103        Returns
104        -------
105        param_names : list
106            List of parameter names.
107
108        """
109        param_names = []
110        for _vary in self.vary:
111            for name in _vary.keys():
112                if not name in param_names:
113                    param_names.append(name)
114        return param_names
115
116    def __next__(self):
117        """
118        Return the next sample from the input distributions.
119
120        Raises
121        ------
122        StopIteration
123            Stop iteration when count >= n_samples.
124
125        Returns
126        -------
127        run_dict : dict
128            A dictionary with the random input samples, e.g.
129            {'x1': 0.5, 'x2': False}.
130
131        """
132        if self.count < self.n_samples():
133            vary_idx = np.where(self.count < self.cumul_sizes[1:])[0][0]
134            run_dict = {}
135            i_par = 0
136            for param_name in self.vary[vary_idx].keys():
137                sample_idx = self.count - self.cumul_sizes[vary_idx]
138                run_dict[param_name] = self.points[vary_idx][sample_idx][i_par]
139                i_par += 1
140            self.count += 1
141            return run_dict
142        else:
143            raise StopIteration
class Grid_Sampler(easyvvuq.sampling.base.BaseSamplingElement):
 43class Grid_Sampler(BaseSamplingElement, sampler_name="grid_sampler"):
 44
 45    def __init__(self, vary, count=0):
 46        """
 47        Initialize the grid sampler.
 48
 49        Parameters
 50        ----------
 51        vary : dict, or list of dicts
 52            A dictionary containing all 1D values for each parameter. For instance
 53            vary = {"x1": [0.0, 0.5. 1.0], "x2": [True, False]}. This will
 54            create a 2D tensor product of all (x1, x2) parameter combinations.
 55            If a list of vary dicts is specified, each vary dict will be treated
 56            independently to generate points. These dicts do not have to contain
 57            the same parameters. The tensor product points are stored in the 
 58            'points' list, with one tensor product per vary dict.
 59        count : int, optional
 60            Internal counter used to count the number of samples that have
 61            been executed. The default is 0.
 62
 63        Returns
 64        -------
 65        None.
 66
 67        """
 68        # allways add vary to list, even if only a single dict is specified
 69        if not isinstance(vary, list):
 70            vary = [vary]
 71
 72        self.vary = vary
 73        self.count = count
 74        self.points = []
 75
 76        # make sure all parameters are stored in a list or array, even
 77        # if they have only a single value
 78        for _vary in vary:
 79            for param in _vary.keys():
 80                if not isinstance(_vary[param], list) and not isinstance(_vary[param], np.ndarray):
 81                    vary[param] = [vary[param]]
 82
 83            # use dtype=object to allow for multiple different type (float, boolean etc)
 84            self.points.append(np.array(list(product(*list(_vary.values()))), dtype=object))
 85
 86        # the cumulative sizes of all ensembles generated by the vary dicts
 87        self.cumul_sizes = np.cumsum([points.shape[0] for points in self.points])
 88        # add a zero to the beginning (necessary in __next__ subroutine)
 89        self.cumul_sizes = np.insert(self.cumul_sizes, 0, 0)
 90
 91    def is_finite(self):
 92        return True
 93
 94    def n_samples(self):
 95        """Returns the number of samples in this sampler.
 96        """
 97        # return self.points.shape[0]
 98        return self.cumul_sizes[-1]
 99
100    def get_param_names(self):
101        """
102        Get the names of all parameters that were varied.
103
104        Returns
105        -------
106        param_names : list
107            List of parameter names.
108
109        """
110        param_names = []
111        for _vary in self.vary:
112            for name in _vary.keys():
113                if not name in param_names:
114                    param_names.append(name)
115        return param_names
116
117    def __next__(self):
118        """
119        Return the next sample from the input distributions.
120
121        Raises
122        ------
123        StopIteration
124            Stop iteration when count >= n_samples.
125
126        Returns
127        -------
128        run_dict : dict
129            A dictionary with the random input samples, e.g.
130            {'x1': 0.5, 'x2': False}.
131
132        """
133        if self.count < self.n_samples():
134            vary_idx = np.where(self.count < self.cumul_sizes[1:])[0][0]
135            run_dict = {}
136            i_par = 0
137            for param_name in self.vary[vary_idx].keys():
138                sample_idx = self.count - self.cumul_sizes[vary_idx]
139                run_dict[param_name] = self.points[vary_idx][sample_idx][i_par]
140                i_par += 1
141            self.count += 1
142            return run_dict
143        else:
144            raise StopIteration

Baseclass for all EasyVVUQ sampling elements.

Attributes
  • sampler_name (str): Name of the particular sampler.
Grid_Sampler(vary, count=0)
45    def __init__(self, vary, count=0):
46        """
47        Initialize the grid sampler.
48
49        Parameters
50        ----------
51        vary : dict, or list of dicts
52            A dictionary containing all 1D values for each parameter. For instance
53            vary = {"x1": [0.0, 0.5. 1.0], "x2": [True, False]}. This will
54            create a 2D tensor product of all (x1, x2) parameter combinations.
55            If a list of vary dicts is specified, each vary dict will be treated
56            independently to generate points. These dicts do not have to contain
57            the same parameters. The tensor product points are stored in the 
58            'points' list, with one tensor product per vary dict.
59        count : int, optional
60            Internal counter used to count the number of samples that have
61            been executed. The default is 0.
62
63        Returns
64        -------
65        None.
66
67        """
68        # allways add vary to list, even if only a single dict is specified
69        if not isinstance(vary, list):
70            vary = [vary]
71
72        self.vary = vary
73        self.count = count
74        self.points = []
75
76        # make sure all parameters are stored in a list or array, even
77        # if they have only a single value
78        for _vary in vary:
79            for param in _vary.keys():
80                if not isinstance(_vary[param], list) and not isinstance(_vary[param], np.ndarray):
81                    vary[param] = [vary[param]]
82
83            # use dtype=object to allow for multiple different type (float, boolean etc)
84            self.points.append(np.array(list(product(*list(_vary.values()))), dtype=object))
85
86        # the cumulative sizes of all ensembles generated by the vary dicts
87        self.cumul_sizes = np.cumsum([points.shape[0] for points in self.points])
88        # add a zero to the beginning (necessary in __next__ subroutine)
89        self.cumul_sizes = np.insert(self.cumul_sizes, 0, 0)

Initialize the grid sampler.

Parameters
  • vary (dict, or list of dicts): A dictionary containing all 1D values for each parameter. For instance vary = {"x1": [0.0, 0.5. 1.0], "x2": [True, False]}. This will create a 2D tensor product of all (x1, x2) parameter combinations. If a list of vary dicts is specified, each vary dict will be treated independently to generate points. These dicts do not have to contain the same parameters. The tensor product points are stored in the 'points' list, with one tensor product per vary dict.
  • count (int, optional): Internal counter used to count the number of samples that have been executed. The default is 0.
Returns
  • None.
vary
count
points
cumul_sizes
def is_finite(self):
91    def is_finite(self):
92        return True
def n_samples(self):
94    def n_samples(self):
95        """Returns the number of samples in this sampler.
96        """
97        # return self.points.shape[0]
98        return self.cumul_sizes[-1]

Returns the number of samples in this sampler.

def get_param_names(self):
100    def get_param_names(self):
101        """
102        Get the names of all parameters that were varied.
103
104        Returns
105        -------
106        param_names : list
107            List of parameter names.
108
109        """
110        param_names = []
111        for _vary in self.vary:
112            for name in _vary.keys():
113                if not name in param_names:
114                    param_names.append(name)
115        return param_names

Get the names of all parameters that were varied.

Returns
  • param_names (list): List of parameter names.
sampler_name = 'grid_sampler'